This is an automated email from the ASF dual-hosted git repository. dangogh pushed a commit to branch master in repository https://gitbox.apache.org/repos/asf/incubator-trafficcontrol.git
commit b844bf97396f456839dbd721605fe69b4d4393ad Author: Dewayne Richardson <dewr...@apache.org> AuthorDate: Fri Apr 6 13:13:48 2018 -0600 added support for attaching parameters to profiles with an id query parameter --- lib/go-tc/v13/parameters.go | 56 +++++++++++++++++ lib/go-tc/v13/profiles.go | 2 + .../traffic_ops_golang/parameter/parameters.go | 7 ++- traffic_ops/traffic_ops_golang/profile/profiles.go | 70 ++++++++++++++++++++-- 4 files changed, 128 insertions(+), 7 deletions(-) diff --git a/lib/go-tc/v13/parameters.go b/lib/go-tc/v13/parameters.go new file mode 100644 index 0000000..e02d9b5 --- /dev/null +++ b/lib/go-tc/v13/parameters.go @@ -0,0 +1,56 @@ +package v13 + +import ( + "encoding/json" + + tc "github.com/apache/incubator-trafficcontrol/lib/go-tc" +) + +/* + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ + +// ParametersResponse ... +type ParametersResponse struct { + Response []Parameter `json:"response"` +} + +// Parameter ... +type Parameter struct { + ConfigFile string `json:"configFile" db:"config_file"` + ID int `json:"id" db:"id"` + LastUpdated tc.TimeNoMod `json:"lastUpdated" db:"last_updated"` + Name string `json:"name" db:"name"` + Profiles json.RawMessage `json:"profiles" db:"profiles"` + Secure bool `json:"secure" db:"secure"` + Value string `json:"value" db:"value"` +} + +// ParameterNullable - a struct version that allows for all fields to be null, mostly used by the API side +type ParameterNullable struct { + // + // NOTE: the db: struct tags are used for testing to map to their equivalent database column (if there is one) + // + ConfigFile *string `json:"configFile" db:"config_file"` + ID *int `json:"id" db:"id"` + LastUpdated *tc.TimeNoMod `json:"lastUpdated" db:"last_updated"` + Name *string `json:"name" db:"name"` + Profiles json.RawMessage `json:"profiles" db:"profiles"` + Secure *bool `json:"secure" db:"secure"` + Value *string `json:"value" db:"value"` +} diff --git a/lib/go-tc/v13/profiles.go b/lib/go-tc/v13/profiles.go index 19899b4..098e331 100644 --- a/lib/go-tc/v13/profiles.go +++ b/lib/go-tc/v13/profiles.go @@ -84,4 +84,6 @@ type ProfileNullable struct { // The Type name associated with the Profile // Type *string `json:"type" db:"type"` + + Parameters []ParameterNullable `json:"params"` } diff --git a/traffic_ops/traffic_ops_golang/parameter/parameters.go b/traffic_ops/traffic_ops_golang/parameter/parameters.go index 7d1af69..6eb6b30 100644 --- a/traffic_ops/traffic_ops_golang/parameter/parameters.go +++ b/traffic_ops/traffic_ops_golang/parameter/parameters.go @@ -44,6 +44,10 @@ const ( ValueQueryParam = "value" ) +var ( + HiddenField = "********" +) + //we need a type alias to define functions on type TOParameter tc.ParameterNullable @@ -214,7 +218,6 @@ func (parameter *TOParameter) Read(db *sqlx.DB, parameters map[string]string, us defer rows.Close() params := []interface{}{} - hiddenField := "********" for rows.Next() { var p tc.ParameterNullable if err = rows.StructScan(&p); err != nil { @@ -227,7 +230,7 @@ func (parameter *TOParameter) Read(db *sqlx.DB, parameters map[string]string, us } if isSecure && (privLevel < auth.PrivLevelAdmin) { - p.Value = &hiddenField + p.Value = &HiddenField } params = append(params, p) } diff --git a/traffic_ops/traffic_ops_golang/profile/profiles.go b/traffic_ops/traffic_ops_golang/profile/profiles.go index 189ba54..d848c6e 100644 --- a/traffic_ops/traffic_ops_golang/profile/profiles.go +++ b/traffic_ops/traffic_ops_golang/profile/profiles.go @@ -30,6 +30,7 @@ import ( "github.com/apache/incubator-trafficcontrol/traffic_ops/traffic_ops_golang/api" "github.com/apache/incubator-trafficcontrol/traffic_ops/traffic_ops_golang/auth" "github.com/apache/incubator-trafficcontrol/traffic_ops/traffic_ops_golang/dbhelpers" + "github.com/apache/incubator-trafficcontrol/traffic_ops/traffic_ops_golang/parameter" "github.com/apache/incubator-trafficcontrol/traffic_ops/traffic_ops_golang/tovalidate" validation "github.com/go-ozzo/ozzo-validation" "github.com/jmoiron/sqlx" @@ -46,6 +47,7 @@ const ( //we need a type alias to define functions on type TOProfile v13.ProfileNullable +type TOParameter v13.ParameterNullable //the refType is passed into the handlers where a copy of its type is used to decode the json. var refType = TOProfile{} @@ -112,7 +114,7 @@ func (prof *TOProfile) Read(db *sqlx.DB, parameters map[string]string, user auth return nil, errs, tc.DataConflictError } - query := selectQuery() + where + orderBy + query := selectProfilesQuery() + where + orderBy log.Debugln("Query is ", query) rows, err := db.NamedQuery(query, queryValues) @@ -124,11 +126,21 @@ func (prof *TOProfile) Read(db *sqlx.DB, parameters map[string]string, user auth profiles := []interface{}{} for rows.Next() { - var p tc.ProfileNullable + var p v13.ProfileNullable if err = rows.StructScan(&p); err != nil { log.Errorf("error parsing Profile rows: %v", err) return nil, []error{tc.DBError}, tc.SystemError } + + // Attach Parameters if the 'id' parameter is sent + if _, ok := parameters[IDQueryParam]; ok { + params, err := ReadParameters(db, parameters, user, p) + p.Parameters = params + if len(errs) > 0 { + log.Errorf("Error getting Parameters: %v", err) + return nil, []error{tc.DBError}, tc.SystemError + } + } profiles = append(profiles, p) } @@ -136,7 +148,7 @@ func (prof *TOProfile) Read(db *sqlx.DB, parameters map[string]string, user auth } -func selectQuery() string { +func selectProfilesQuery() string { query := `SELECT prof.description, @@ -153,6 +165,56 @@ JOIN cdn c ON prof.cdn = c.id` return query } +func ReadParameters(db *sqlx.DB, parameters map[string]string, user auth.CurrentUser, profile v13.ProfileNullable) ([]v13.ParameterNullable, []error) { + + var rows *sqlx.Rows + privLevel := user.PrivLevel + queryValues := make(map[string]interface{}) + queryValues["profile_id"] = *profile.ID + + query := selectParametersQuery() + rows, err := db.NamedQuery(query, queryValues) + if err != nil { + log.Errorf("Error querying Parameter: %v", err) + return nil, []error{tc.DBError} + } + defer rows.Close() + + var params []v13.ParameterNullable + for rows.Next() { + var param v13.ParameterNullable + + if err = rows.StructScan(¶m); err != nil { + log.Errorf("error parsing parameter rows: %v", err) + return nil, []error{tc.DBError} + } + var isSecure bool + if param.Secure != nil { + isSecure = *param.Secure + } + if isSecure && (privLevel < auth.PrivLevelAdmin) { + param.Value = ¶meter.HiddenField + } + params = append(params, param) + } + return params, []error{} +} + +func selectParametersQuery() string { + + query := `SELECT +p.id, +p.name, +p.config_file, +p.value, +p.secure +FROM parameter p +JOIN profile_parameter pp ON pp.parameter = p.id +WHERE pp.profile = :profile_id` + + return query +} + //The TOProfile implementation of the Updater interface //all implementations of Updater should use transactions and return the proper errorType //ParsePQUniqueConstraintError is used to determine if a profile with conflicting values exists @@ -240,8 +302,6 @@ func (prof *TOProfile) Create(db *sqlx.DB, user auth.CurrentUser) (error, tc.Api log.Error.Printf("could not begin transaction: %v", err) return tc.DBError, tc.SystemError } - q := insertQuery() - fmt.Printf("q ---> %v\n", q) resultRows, err := tx.NamedQuery(insertQuery(), prof) if err != nil { if pqErr, ok := err.(*pq.Error); ok { -- To stop receiving notification emails like this one, please contact dang...@apache.org.