From 74dae6dad93b990e473a5b83dfffbbcd42b4e548 Mon Sep 17 00:00:00 2001 From: "A.Unger" Date: Mon, 8 Nov 2021 11:14:26 +0100 Subject: [PATCH] add ocis-pkg/config default config + fix logging inheritance --- ocis-pkg/config/config.go | 126 +++++++++++++++++++++++-- ocis-pkg/config/environment.go | 11 +-- ocis/pkg/command/proxy.go | 25 +---- ocis/pkg/command/root.go | 5 +- ocis/pkg/command/server.go | 4 +- ocis/pkg/config/config.go | 1 - ocis/pkg/flagset/flagset.go | 164 +-------------------------------- proxy/pkg/command/root.go | 25 ++--- proxy/pkg/config/config.go | 8 +- proxy/pkg/config/env.go | 17 ---- proxy/pkg/config/mappings.go | 15 ++- 11 files changed, 152 insertions(+), 249 deletions(-) delete mode 100644 ocis/pkg/config/config.go delete mode 100644 proxy/pkg/config/env.go diff --git a/ocis-pkg/config/config.go b/ocis-pkg/config/config.go index 5e97e79c9..1b8f7e963 100644 --- a/ocis-pkg/config/config.go +++ b/ocis-pkg/config/config.go @@ -82,10 +82,7 @@ type Runtime struct { // Config combines all available configuration parts. type Config struct { - // Mode is mostly used whenever we need to run an extension. The technical debt this introduces is in regard of - // what it does. Supervised (0) loads configuration from a unified config file because of known limitations of Viper; whereas - // Unsupervised (1) MUST parse config from all known sources. - Mode Mode + Mode Mode // DEPRECATED File string OcisURL string `mapstructure:"ocis_url"` @@ -132,6 +129,54 @@ func New() *Config { } } +func DefaultConfig() *Config { + return &Config{ + Log: Log{ + Level: "info", + }, + Debug: Debug{ + Addr: "127.0.0.1:9010", + Token: "", + Pprof: false, + Zpages: false, + }, + HTTP: HTTP{ + Addr: "127.0.0.1:9000", + Root: "/", + }, + GRPC: GRPC{ + Addr: "127.0.0.1:9001", + }, + Tracing: Tracing{ + Enabled: false, + Type: "jaeger", + Endpoint: "", + Collector: "", + Service: "ocis", + }, + TokenManager: TokenManager{ + JWTSecret: "Pive-Fumkiu4", + }, + Runtime: Runtime{ + Port: "9250", + Host: "localhost", + }, + Accounts: accounts.DefaultConfig(), + GLAuth: glauth.DefaultConfig(), + Graph: graph.DefaultConfig(), + IDP: idp.DefaultConfig(), + Proxy: proxy.DefaultConfig(), + GraphExplorer: graphExplorer.DefaultConfig(), + OCS: ocs.DefaultConfig(), + Settings: settings.DefaultConfig(), + Web: web.DefaultConfig(), + Store: store.DefaultConfig(), + Thumbnails: thumbnails.DefaultConfig(), + WebDAV: webdav.DefaultConfig(), + Storage: storage.New(), + } +} + // GetEnv fetches a list of known env variables for this extension. It is to be used by gookit, as it provides a list // with all the environment variables an extension supports. func GetEnv() []string { @@ -178,13 +223,8 @@ func (c *Config) UnmapEnv(gooconf *gofig.Config) error { return nil } -// structMappings binds a set of environment variables to a destination on cfg. func structMappings(cfg *Config) []shared.EnvBinding { return []shared.EnvBinding{ - { - EnvVars: []string{"OCIS_LOG_FILE"}, - Destination: &cfg.Log.Level, - }, { EnvVars: []string{"OCIS_LOG_LEVEL"}, Destination: &cfg.Log.Level, @@ -197,5 +237,73 @@ func structMappings(cfg *Config) []shared.EnvBinding { EnvVars: []string{"OCIS_LOG_PRETTY"}, Destination: &cfg.Log.Pretty, }, + { + EnvVars: []string{"OCIS_LOG_FILE"}, + Destination: &cfg.Log.File, + }, + { + EnvVars: []string{"OCIS_TRACING_ENABLED"}, + Destination: &cfg.Tracing.Enabled, + }, + { + EnvVars: []string{"OCIS_TRACING_TYPE"}, + Destination: &cfg.Tracing.Type, + }, + { + EnvVars: []string{"OCIS_TRACING_ENDPOINT"}, + Destination: &cfg.Tracing.Endpoint, + }, + { + EnvVars: []string{"OCIS_TRACING_COLLECTOR"}, + Destination: &cfg.Tracing.Collector, + }, + { + EnvVars: []string{"OCIS_TRACING_SERVICE"}, + Destination: &cfg.Tracing.Service, + }, + { + EnvVars: []string{"OCIS_JWT_SECRET"}, + Destination: &cfg.TokenManager.JWTSecret, + }, + { + EnvVars: []string{"OCIS_RUNTIME_PORT"}, + Destination: &cfg.Runtime.Port, + }, + { + EnvVars: []string{"OCIS_RUNTIME_HOST"}, + Destination: &cfg.Runtime.Host, + }, + { + EnvVars: []string{"OCIS_DEBUG_ADDR"}, + Destination: &cfg.Debug.Addr, + }, + { + EnvVars: []string{"OCIS_DEBUG_TOKEN"}, + Destination: &cfg.Debug.Token, + }, + { + EnvVars: []string{"OCIS_DEBUG_PPROF"}, + Destination: &cfg.Debug.Pprof, + }, + { + EnvVars: []string{"OCIS_DEBUG_ZPAGES"}, + Destination: &cfg.Debug.Zpages, + }, + { + EnvVars: []string{"OCIS_HTTP_ADDR"}, + Destination: &cfg.HTTP.Addr, + }, + { + EnvVars: []string{"OCIS_HTTP_ROOT"}, + Destination: &cfg.HTTP.Root, + }, + { + EnvVars: []string{"OCIS_GRPC_ADDR"}, + Destination: &cfg.GRPC.Addr, + }, + { + EnvVars: []string{"OCIS_RUN_EXTENSIONS"}, + Destination: &cfg.Runtime.Extensions, + }, } } diff --git a/ocis-pkg/config/environment.go b/ocis-pkg/config/environment.go index 14d62609c..c713d92e4 100644 --- a/ocis-pkg/config/environment.go +++ b/ocis-pkg/config/environment.go @@ -4,17 +4,16 @@ import ( "fmt" "reflect" - "github.com/owncloud/ocis/ocis-pkg/shared" - gofig "github.com/gookit/config/v2" + "github.com/owncloud/ocis/ocis-pkg/shared" ) -// UnbindEnv takes a config `c` and a EnvBinding -func UnbindEnv(c *gofig.Config, bindings []shared.EnvBinding) error { - return unbindEnv(c, bindings) +// BindEnv takes a config `c` and a EnvBinding and binds the values from the environment to the address location in cfg. +func BindEnv(c *gofig.Config, bindings []shared.EnvBinding) error { + return bindEnv(c, bindings) } -func unbindEnv(c *gofig.Config, bindings []shared.EnvBinding) error { +func bindEnv(c *gofig.Config, bindings []shared.EnvBinding) error { for i := range bindings { for j := range bindings[i].EnvVars { // we need to guard against v != "" because this is the condition that checks that the value is set from the environment. diff --git a/ocis/pkg/command/proxy.go b/ocis/pkg/command/proxy.go index 29ea6b73b..df4e86562 100644 --- a/ocis/pkg/command/proxy.go +++ b/ocis/pkg/command/proxy.go @@ -5,10 +5,8 @@ package command import ( "github.com/owncloud/ocis/ocis-pkg/config" - "github.com/owncloud/ocis/ocis-pkg/version" "github.com/owncloud/ocis/ocis/pkg/register" "github.com/owncloud/ocis/proxy/pkg/command" - svcconfig "github.com/owncloud/ocis/proxy/pkg/config" "github.com/urfave/cli/v2" ) @@ -25,33 +23,12 @@ func ProxyCommand(cfg *config.Config) *cli.Command { return ParseConfig(ctx, cfg) }, Action: func(c *cli.Context) error { - origCmd := command.Server(configureProxy(cfg)) + origCmd := command.Server(cfg.Proxy) return handleOriginalAction(c, origCmd) }, } } -func configureProxy(cfg *config.Config) *svcconfig.Config { - cfg.Proxy.OcisURL = cfg.OcisURL - cfg.Proxy.Log.Level = cfg.Log.Level - cfg.Proxy.Log.Pretty = cfg.Log.Pretty - cfg.Proxy.Log.Color = cfg.Log.Color - cfg.Proxy.Service.Version = version.String - - if cfg.Tracing.Enabled { - cfg.Proxy.Tracing.Enabled = cfg.Tracing.Enabled - cfg.Proxy.Tracing.Type = cfg.Tracing.Type - cfg.Proxy.Tracing.Endpoint = cfg.Tracing.Endpoint - cfg.Proxy.Tracing.Collector = cfg.Tracing.Collector - } - - if cfg.TokenManager.JWTSecret != "" { - cfg.Proxy.TokenManager.JWTSecret = cfg.TokenManager.JWTSecret - } - - return cfg.Proxy -} - func init() { register.AddCommand(ProxyCommand) } diff --git a/ocis/pkg/command/root.go b/ocis/pkg/command/root.go index cd2b49eb0..4750c986b 100644 --- a/ocis/pkg/command/root.go +++ b/ocis/pkg/command/root.go @@ -3,8 +3,6 @@ package command import ( "os" - "github.com/owncloud/ocis/ocis/pkg/flagset" - "github.com/owncloud/ocis/ocis-pkg/config" ociscfg "github.com/owncloud/ocis/ocis-pkg/config" "github.com/owncloud/ocis/ocis-pkg/log" @@ -15,14 +13,13 @@ import ( // Execute is the entry point for the ocis command. func Execute() error { - cfg := config.New() + cfg := config.DefaultConfig() app := &cli.App{ Name: "ocis", Version: version.String, Usage: "ownCloud Infinite Scale Stack", Compiled: version.Compiled(), - Flags: flagset.RootWithConfig(cfg), Before: func(c *cli.Context) error { return ParseConfig(c, cfg) }, diff --git a/ocis/pkg/command/server.go b/ocis/pkg/command/server.go index acd66bc26..0863c5746 100644 --- a/ocis/pkg/command/server.go +++ b/ocis/pkg/command/server.go @@ -7,7 +7,6 @@ import ( "strings" "github.com/owncloud/ocis/ocis-pkg/config" - "github.com/owncloud/ocis/ocis/pkg/flagset" "github.com/owncloud/ocis/ocis/pkg/register" "github.com/owncloud/ocis/ocis/pkg/runtime" "github.com/urfave/cli/v2" @@ -19,13 +18,12 @@ func Server(cfg *config.Config) *cli.Command { Name: "server", Usage: "Start fullstack server", Category: "Fullstack", - Flags: flagset.ServerWithConfig(cfg), Before: func(c *cli.Context) error { if cfg.HTTP.Root != "/" { cfg.HTTP.Root = strings.TrimSuffix(cfg.HTTP.Root, "/") } - return nil + return ParseConfig(c, cfg) }, Action: func(c *cli.Context) error { r := runtime.New(cfg) diff --git a/ocis/pkg/config/config.go b/ocis/pkg/config/config.go deleted file mode 100644 index d912156be..000000000 --- a/ocis/pkg/config/config.go +++ /dev/null @@ -1 +0,0 @@ -package config diff --git a/ocis/pkg/flagset/flagset.go b/ocis/pkg/flagset/flagset.go index 68bcdb14a..1450838fc 100644 --- a/ocis/pkg/flagset/flagset.go +++ b/ocis/pkg/flagset/flagset.go @@ -5,109 +5,7 @@ import ( "github.com/urfave/cli/v2" ) -// RootWithConfig applies cfg to the root flagset -func RootWithConfig(cfg *config.Config) []cli.Flag { - return []cli.Flag{ - &cli.StringFlag{ - // this is just a dummy config flag do document the existence - // of this environment variable - // the environment variable itself is used in `ocis-pkg/config/defaults/paths.go` - Name: "ocis-base-data-path", - Usage: "Set the base path where oCIS stores data", - EnvVars: []string{"OCIS_BASE_DATA_PATH"}, - }, - &cli.StringFlag{ - Name: "config-file", - Usage: "Load config file from a non standard location.", - EnvVars: []string{"OCIS_CONFIG_FILE"}, - Destination: &cfg.File, - }, - &cli.StringFlag{ - Name: "ocis-log-level", - Value: "info", - Usage: "Set logging level", - EnvVars: []string{"OCIS_LOG_LEVEL"}, - Destination: &cfg.Log.Level, - }, - &cli.BoolFlag{ - Value: false, - Name: "ocis-log-pretty", - Usage: "Enable pretty logging", - EnvVars: []string{"OCIS_LOG_PRETTY"}, - Destination: &cfg.Log.Pretty, - }, - &cli.BoolFlag{ - Value: true, - Name: "ocis-log-color", - Usage: "Enable colored logging", - EnvVars: []string{"OCIS_LOG_COLOR"}, - Destination: &cfg.Log.Color, - }, - &cli.StringFlag{ - Name: "ocis-log-file", - Usage: "Enable log to file", - EnvVars: []string{"OCIS_LOG_FILE"}, - Destination: &cfg.Log.File, - }, - &cli.BoolFlag{ - Name: "tracing-enabled", - Usage: "Enable sending traces", - EnvVars: []string{"OCIS_TRACING_ENABLED"}, - Destination: &cfg.Tracing.Enabled, - }, - &cli.StringFlag{ - Name: "tracing-type", - Value: "jaeger", - Usage: "Tracing backend type", - EnvVars: []string{"OCIS_TRACING_TYPE"}, - Destination: &cfg.Tracing.Type, - }, - &cli.StringFlag{ - Name: "tracing-endpoint", - Value: "", - Usage: "Endpoint for the agent", - EnvVars: []string{"OCIS_TRACING_ENDPOINT"}, - Destination: &cfg.Tracing.Endpoint, - }, - &cli.StringFlag{ - Name: "tracing-collector", - Value: "", - Usage: "Endpoint for the collector", - EnvVars: []string{"OCIS_TRACING_COLLECTOR"}, - Destination: &cfg.Tracing.Collector, - }, - &cli.StringFlag{ - Name: "tracing-service", - Value: "ocis", - Usage: "Service name for tracing", - EnvVars: []string{"OCIS_TRACING_SERVICE"}, - Destination: &cfg.Tracing.Service, - }, - &cli.StringFlag{ - Name: "jwt-secret", - Value: "Pive-Fumkiu4", - Usage: "Used to dismantle the access token, should equal reva's jwt-secret", - EnvVars: []string{"OCIS_JWT_SECRET"}, - Destination: &cfg.TokenManager.JWTSecret, - }, - &cli.StringFlag{ - Name: "runtime-port", - Value: "9250", - Usage: "Configures which port the runtime starts", - EnvVars: []string{"OCIS_RUNTIME_PORT"}, - Destination: &cfg.Runtime.Port, - }, - &cli.StringFlag{ - Name: "runtime-host", - Value: "localhost", - Usage: "Configures the host where the runtime process is running", - EnvVars: []string{"OCIS_RUNTIME_HOST"}, - Destination: &cfg.Runtime.Host, - }, - } -} - -// HealthWithConfig applies cfg to the root flagset +// HealthWithConfig applies cfg to the root flag-set. func HealthWithConfig(cfg *config.Config) []cli.Flag { return []cli.Flag{ &cli.StringFlag{ @@ -119,63 +17,3 @@ func HealthWithConfig(cfg *config.Config) []cli.Flag { }, } } - -// ServerWithConfig applies cfg to the root flagset -func ServerWithConfig(cfg *config.Config) []cli.Flag { - return []cli.Flag{ - &cli.StringFlag{ - Name: "debug-addr", - Value: "127.0.0.1:9010", - Usage: "Address to bind debug server", - EnvVars: []string{"OCIS_DEBUG_ADDR"}, - Destination: &cfg.Debug.Addr, - }, - &cli.StringFlag{ - Name: "debug-token", - Value: "", - Usage: "Token to grant metrics access", - EnvVars: []string{"OCIS_DEBUG_TOKEN"}, - Destination: &cfg.Debug.Token, - }, - &cli.BoolFlag{ - Name: "debug-pprof", - Usage: "Enable pprof debugging", - EnvVars: []string{"OCIS_DEBUG_PPROF"}, - Destination: &cfg.Debug.Pprof, - }, - &cli.BoolFlag{ - Name: "debug-zpages", - Usage: "Enable zpages debugging", - EnvVars: []string{"OCIS_DEBUG_ZPAGES"}, - Destination: &cfg.Debug.Zpages, - }, - &cli.StringFlag{ - Name: "http-addr", - Value: "127.0.0.1:9000", - Usage: "Address to bind http server", - EnvVars: []string{"OCIS_HTTP_ADDR"}, - Destination: &cfg.HTTP.Addr, - }, - &cli.StringFlag{ - Name: "http-root", - Value: "/", - Usage: "Root path of http server", - EnvVars: []string{"OCIS_HTTP_ROOT"}, - Destination: &cfg.HTTP.Root, - }, - &cli.StringFlag{ - Name: "grpc-addr", - Value: "127.0.0.1:9001", - Usage: "Address to bind grpc server", - EnvVars: []string{"OCIS_GRPC_ADDR"}, - Destination: &cfg.GRPC.Addr, - }, - &cli.StringFlag{ - Name: "extensions", - Aliases: []string{"e"}, - Usage: "Run specific extensions during supervised mode", - EnvVars: []string{"OCIS_RUN_EXTENSIONS"}, - Destination: &cfg.Runtime.Extensions, - }, - } -} diff --git a/proxy/pkg/command/root.go b/proxy/pkg/command/root.go index 9b1430df1..64ecbe874 100644 --- a/proxy/pkg/command/root.go +++ b/proxy/pkg/command/root.go @@ -63,17 +63,22 @@ func NewLogger(cfg *config.Config) log.Logger { ) } -// ParseConfig loads proxy configuration from known paths. +// ParseConfig loads proxy configuration. Loading will first attempt to parse config files in the expected locations +// and then parses environment variables. In the context of oCIS env variables will always overwrite values set +// in a config file. +// If this extension is run as a subcommand (i.e: ocis proxy) then there are 2 levels of config parsing: +// 1. ocis.yaml (if any) +// 2. proxy.yaml (if any) +// 3. environment variables. func ParseConfig(c *cli.Context, cfg *config.Config) error { conf, err := ociscfg.BindSourcesToStructs("proxy", cfg) if err != nil { return err } - // load all env variables relevant to the config in the current context. conf.LoadOSEnv(config.GetEnv(), false) bindings := config.StructMappings(cfg) - return ociscfg.UnbindEnv(conf, bindings) + return ociscfg.BindEnv(conf, bindings) } // SutureService allows for the proxy command to be embedded and supervised by a suture supervisor tree. @@ -83,10 +88,6 @@ type SutureService struct { // NewSutureService creates a new proxy.SutureService func NewSutureService(cfg *ociscfg.Config) suture.Service { - inheritLogging(cfg) - if cfg.Mode == 0 { - cfg.Proxy.Supervised = true - } return SutureService{ cfg: cfg.Proxy, } @@ -100,13 +101,3 @@ func (s SutureService) Serve(ctx context.Context) error { return nil } - -// inheritLogging is a poor man's global logging state tip-toeing around circular dependencies. It sets the logging -// of the service to whatever is in the higher config (in this case coming from ocis.yaml) and sets them as defaults, -// being overwritten when the extension parses its config file / env variables. -func inheritLogging(cfg *ociscfg.Config) { - cfg.Proxy.Log.File = cfg.Log.File - cfg.Proxy.Log.Color = cfg.Log.Color - cfg.Proxy.Log.Pretty = cfg.Log.Pretty - cfg.Proxy.Log.Level = cfg.Log.Level -} diff --git a/proxy/pkg/config/config.go b/proxy/pkg/config/config.go index 9097390fc..f2c16df67 100644 --- a/proxy/pkg/config/config.go +++ b/proxy/pkg/config/config.go @@ -141,10 +141,10 @@ type OIDC struct { // PolicySelector is the toplevel-configuration for different selectors type PolicySelector struct { - Static *StaticSelectorConf - Migration *MigrationSelectorConf - Claims *ClaimsSelectorConf - Regex *RegexSelectorConf + Static *StaticSelectorConf `mapstructure:"static"` + Migration *MigrationSelectorConf `mapstructure:"migration"` + Claims *ClaimsSelectorConf `mapstructure:"claims"` + Regex *RegexSelectorConf `mapstructure:"regex"` } // StaticSelectorConf is the config for the static-policy-selector diff --git a/proxy/pkg/config/env.go b/proxy/pkg/config/env.go deleted file mode 100644 index 0662983e3..000000000 --- a/proxy/pkg/config/env.go +++ /dev/null @@ -1,17 +0,0 @@ -package config - -type mapping struct { - EnvVars []string // name of the EnvVars var. - Destination interface{} // memory address of the original config value to modify. -} - -// GetEnv fetches a list of known env variables for this extension. It is to be used by gookit, as it provides a list -// with all the environment variables an extension supports. -func GetEnv() []string { - var r = make([]string, len(structMappings(&Config{}))) - for i := range structMappings(&Config{}) { - r = append(r, structMappings(&Config{})[i].EnvVars...) - } - - return r -} diff --git a/proxy/pkg/config/mappings.go b/proxy/pkg/config/mappings.go index 5119ff571..fc9433818 100644 --- a/proxy/pkg/config/mappings.go +++ b/proxy/pkg/config/mappings.go @@ -2,7 +2,20 @@ package config import "github.com/owncloud/ocis/ocis-pkg/shared" -// StructMappings binds a set of environment variables to a destination on cfg. +// GetEnv fetches a list of known env variables for this extension. It is to be used by gookit, as it provides a list +// with all the environment variables an extension supports. +func GetEnv() []string { + var r = make([]string, len(structMappings(&Config{}))) + for i := range structMappings(&Config{}) { + r = append(r, structMappings(&Config{})[i].EnvVars...) + } + + return r +} + +// StructMappings binds a set of environment variables to a destination on cfg. Iterating over this set and editing the +// Destination value of a binding will alter the original value, as it is a pointer to its memory address. This lets +// us propagate changes easier. func StructMappings(cfg *Config) []shared.EnvBinding { return structMappings(cfg) }