// Copyright 2018-2021 CERN // // Licensed 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. // // In applying this license, CERN does not waive the privileges and immunities // granted to it by virtue of its status as an Intergovernmental Organization // or submit itself to any jurisdiction. package sharedconf import ( "fmt" "os" "sync" "github.com/mitchellh/mapstructure" ) var ( sharedConf = &conf{} sharedConfOnce sync.Once ) // ClientOptions represent additional options (e.g. tls settings) for the grpc clients type ClientOptions struct { TLSMode string `mapstructure:"tls_mode"` CACertFile string `mapstructure:"cacert"` } type conf struct { JWTSecret string `mapstructure:"jwt_secret"` GatewaySVC string `mapstructure:"gatewaysvc"` DataGateway string `mapstructure:"datagateway"` SkipUserGroupsInToken bool `mapstructure:"skip_user_groups_in_token"` GRPCClientOptions ClientOptions `mapstructure:"grpc_client_options"` } // Decode decodes the configuration. func Decode(v interface{}) error { var err error sharedConfOnce.Do(func() { if err = mapstructure.Decode(v, sharedConf); err != nil { return } // add some defaults if sharedConf.GatewaySVC == "" { sharedConf.GatewaySVC = "0.0.0.0:19000" } // this is the default address we use for the data gateway HTTP service if sharedConf.DataGateway == "" { host, err := os.Hostname() if err != nil || host == "" { sharedConf.DataGateway = "http://0.0.0.0:19001/datagateway" } else { sharedConf.DataGateway = fmt.Sprintf("http://%s:19001/datagateway", host) } } // TODO(labkode): would be cool to autogenerate one secret and print // it on init time. if sharedConf.JWTSecret == "" { sharedConf.JWTSecret = "changemeplease" } }) return err } // GetJWTSecret returns the package level configured jwt secret if not overwritten. func GetJWTSecret(val string) string { if val == "" { return sharedConf.JWTSecret } return val } // GetGatewaySVC returns the package level configured gateway service if not overwritten. func GetGatewaySVC(val string) string { if val == "" { return sharedConf.GatewaySVC } return val } // GetDataGateway returns the package level data gateway endpoint if not overwritten. func GetDataGateway(val string) string { if val == "" { return sharedConf.DataGateway } return val } // SkipUserGroupsInToken returns whether to skip encoding user groups in the access tokens. func SkipUserGroupsInToken() bool { return sharedConf.SkipUserGroupsInToken } // GRPCClientOptions returns the global grpc client options func GRPCClientOptions() ClientOptions { return sharedConf.GRPCClientOptions } // this is used by the tests func resetOnce() { sharedConf = &conf{} sharedConfOnce = sync.Once{} }