Skip to content

Commit

Permalink
fix viper
Browse files Browse the repository at this point in the history
  • Loading branch information
kanishkatn committed May 12, 2023
1 parent 3502891 commit 000b9b4
Show file tree
Hide file tree
Showing 7 changed files with 165 additions and 21 deletions.
4 changes: 4 additions & 0 deletions chain/kusama/defaults.go
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,10 @@ func DefaultConfig() *cfg.Config {
config.ID = defaultID
config.Name = defaultName
config.ChainSpec = defaultChainSpec
config.Core.BabeAuthority = false
config.Core.GrandpaAuthority = false
config.Core.Role = 1
config.Network.NoMDNS = false

return config
}
4 changes: 4 additions & 0 deletions chain/polkadot/defaults.go
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,10 @@ func DefaultConfig() *cfg.Config {
config.ID = defaultID
config.Name = defaultName
config.ChainSpec = defaultChainSpec
config.Core.BabeAuthority = false
config.Core.GrandpaAuthority = false
config.Core.Role = 1
config.Network.NoMDNS = false

return config
}
4 changes: 4 additions & 0 deletions chain/westend/defaults.go
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,10 @@ func DefaultConfig() *cfg.Config {
config.ID = defaultID
config.Name = defaultName
config.ChainSpec = defaultChainSpec
config.Core.BabeAuthority = false
config.Core.GrandpaAuthority = false
config.Core.Role = 1
config.Network.NoMDNS = false

return config
}
28 changes: 13 additions & 15 deletions cmd/gossamer/commands/root.go
Original file line number Diff line number Diff line change
Expand Up @@ -7,13 +7,14 @@ import (
"fmt"
"os"

"github.com/ChainSafe/gossamer/dot"

"github.com/ChainSafe/gossamer/lib/keystore"

cfg "github.com/ChainSafe/gossamer/config"

"github.com/ChainSafe/gossamer/internal/log"

"github.com/ChainSafe/gossamer/dot"
"github.com/spf13/cobra"
)

Expand Down Expand Up @@ -128,7 +129,7 @@ Usage:
}

if cmd.Name() == "gossamer" {
if err := configureViper(config.BasePath); err != nil {
if err := configureViper(config.BasePath, cmd); err != nil {
return fmt.Errorf("failed to configure viper: %s", err)
}

Expand Down Expand Up @@ -283,29 +284,26 @@ func addLogFlags(cmd *cobra.Command) {

// addAccountFlags adds account flags and binds to viper
func addAccountFlags(cmd *cobra.Command) error {
cmd.PersistentFlags().StringVar(&key,
cmd.Flags().StringVar(&key,
"key",
"",
"Keyring to use for the node")

if err := addStringFlagBindViper(cmd,
cmd.PersistentFlags().String(
"unlock",
config.Account.Unlock,
"Unlock an account. eg. --unlock=0 to unlock account 0.",
"account.unlock"); err != nil {
return fmt.Errorf("failed to add --unlock flag: %s", err)
}
"Unlock an account. eg. --unlock=0 to unlock account 0.")

// Default Account flags
cmd.PersistentFlags().BoolVar(&alice,
cmd.Flags().BoolVar(&alice,
"alice",
false,
"use Alice's key")
cmd.PersistentFlags().BoolVar(&bob,
cmd.Flags().BoolVar(&bob,
"bob",
false,
"use Bob's key")
cmd.PersistentFlags().BoolVar(&charlie,
cmd.Flags().BoolVar(&charlie,
"charlie",
false,
"use Charlie's key")
Expand Down Expand Up @@ -566,16 +564,16 @@ func addStateFlags(cmd *cobra.Command) error {

// addPprofFlags adds pprof flags and binds to viper
func addPprofFlags(cmd *cobra.Command) {
cmd.Flags().Bool("pprof.enabled",
cmd.PersistentFlags().Bool("pprof.enabled",
config.Pprof.Enabled,
"enabled")
cmd.Flags().String("pprof.listening-address",
cmd.PersistentFlags().String("pprof.listening-address",
config.Pprof.ListeningAddress,
"Address to listen on for pprof")
cmd.Flags().Int("pprof.block-profile-rate",
cmd.PersistentFlags().Int("pprof.block-profile-rate",
config.Pprof.BlockProfileRate,
"The frequency at which the Go runtime samples the state of goroutines to generate block profile information.")
cmd.Flags().Int("pprof.mutex-profile-rate",
cmd.PersistentFlags().Int("pprof.mutex-profile-rate",
config.Pprof.MutexProfileRate,
"The frequency at which the Go runtime samples the state of mutexes to generate mutex profile information.")
}
Expand Down
80 changes: 76 additions & 4 deletions cmd/gossamer/commands/utils.go
Original file line number Diff line number Diff line change
Expand Up @@ -7,11 +7,14 @@ import (
"fmt"
"os"
"path/filepath"
"reflect"
"strconv"
"strings"
"syscall"
"time"

"github.com/spf13/cobra"

"github.com/ChainSafe/gossamer/chain/kusama"
"github.com/ChainSafe/gossamer/chain/polkadot"
"github.com/ChainSafe/gossamer/chain/westend"
Expand All @@ -29,7 +32,6 @@ import (
"github.com/ChainSafe/gossamer/lib/keystore"
"github.com/ChainSafe/gossamer/lib/utils"

"github.com/spf13/cobra"
"github.com/spf13/viper"
)

Expand Down Expand Up @@ -244,15 +246,27 @@ func parseChainSpec(chain string) error {
}
}

// parse chain spec and set config fields
spec, err := genesis.NewGenesisFromJSONRaw(config.ChainSpec)
if err != nil {
return fmt.Errorf("failed to load chain spec: %s", err)
}

config.ID = spec.ID
config.Network.Bootnodes = spec.Bootnodes
config.Network.ProtocolID = spec.ProtocolID

return nil
}

// configureViper sets up viper to read from the config file and command line flags
func configureViper(basePath string) error {
func configureViper(basePath string, cmd *cobra.Command) error {
viper.SetConfigName("config") // name of config file (without extension)
viper.AddConfigPath(basePath) // search `base-path`
viper.AddConfigPath(filepath.Join(basePath, "config")) // search `base-path/config`

setViperDefault(config)

// If a config file is found, read it in.
if err := viper.ReadInConfig(); err != nil {
if _, ok := err.(viper.ConfigFileNotFoundError); !ok {
Expand Down Expand Up @@ -349,7 +363,6 @@ func copyChainSpec(source, destination string) error {
config.ChainSpec = destination
// bind it to viper so that it can be used during the config parsing
viper.Set("chain-spec", destination)

return nil
}

Expand Down Expand Up @@ -406,6 +419,65 @@ func parseTelemetryURL() error {
}

viper.Set("telemetry-url", config.TelemetryURLs)

return nil
}

// setViperDefault sets the default values for the config
// The method goes through the config struct and binds each field to viper
// in the format <parent-name>.<field-name> = <field-value>
// The name of the field is taken from the mapstructure tag
func setViperDefault(config *cfg.Config) {
configType := reflect.TypeOf(*config)
configValue := reflect.ValueOf(*config)

for i := 0; i < configType.NumField(); i++ {
field := configType.Field(i)

mapstructureTag := field.Tag.Get("mapstructure")
if mapstructureTag == "" {
continue
}

tagParts := strings.Split(mapstructureTag, ",")
if len(tagParts) > 0 && tagParts[0] == "-" {
continue
}

parentPrefix := tagParts[0]
if field.Type.Kind() == reflect.Struct || field.Type.Kind() == reflect.Ptr {
subType := field.Type
if subType.Kind() == reflect.Ptr {
subType = subType.Elem()
}

for j := 0; j < subType.NumField(); j++ {
subField := subType.Field(j)
subMapstructureTag := subField.Tag.Get("mapstructure")
if subMapstructureTag == "" {
continue
}

subTagParts := strings.Split(subMapstructureTag, ",")
if len(subTagParts) > 0 && subTagParts[0] == "-" {
continue
}

prefix := subTagParts[0]
if parentPrefix != "" {
prefix = parentPrefix + "." + subTagParts[0]
}

var value interface{}
if configValue.Field(i).Kind() == reflect.Ptr {
value = configValue.Field(i).Elem().Field(j).Interface()
} else {
value = configValue.Field(i).Field(j).Interface()
}

if !viper.IsSet(prefix) {
viper.SetDefault(prefix, value)
}
}
}
}
}
62 changes: 62 additions & 0 deletions cmd/gossamer/commands/utils_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,12 @@ import (
"time"

"github.com/spf13/cobra"

"github.com/stretchr/testify/require"

"github.com/spf13/viper"

"github.com/ChainSafe/gossamer/chain/westend"
)

func TestAddStringFlagBindViper(t *testing.T) {
Expand Down Expand Up @@ -204,3 +209,60 @@ func TestAddStringSliceFlagBindViper(t *testing.T) {
t.Fatalf("Expected Viper value 'testBindName' to be ['value1', 'value2'], got '%v'", viperValue)
}
}

func TestBindToViper(t *testing.T) {
t.Parallel()

config = westend.DefaultConfig()
setViperDefault(config)

tests := []struct {
name string
expected any
result any
}{
{
expected: config.Name,
result: viper.Get("name"),
},
{
expected: config.ID,
result: viper.Get("id"),
},
{
expected: config.BasePath,
result: viper.Get("basepath"),
},
{
expected: config.LogLevel,
result: viper.Get("log-level"),
},
{
expected: config.Log.Core,
result: viper.Get("log.core"),
},
{
expected: config.Core.Role,
result: viper.Get("core.role"),
},
{
expected: config.Network.NoMDNS,
result: viper.Get("network.nomdns"),
},
{
expected: config.RPC.Port,
result: viper.Get("rpc.port"),
},
{
expected: config.Account.Key,
result: viper.Get("account.key"),
},
}

for _, tt := range tests {
t.Run(tt.name, func(t *testing.T) {
t.Parallel()
require.Equal(t, tt.expected, tt.result)
})
}
}
4 changes: 2 additions & 2 deletions config/config.go
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,7 @@ const (
// defaultChainSpecFile is the default genesis file
defaultChainSpecFile = "chain-spec-raw.json"
// defaultBasePath is the default base path
defaultBasePath = "~/.gossamer"
defaultBasePath = "~/.gossamer/gssmr"
// DefaultLogLevel is the default log level
DefaultLogLevel = "info"
// DefaultPrometheusPort is the default prometheus port
Expand Down Expand Up @@ -436,7 +436,7 @@ func DefaultConfigFromSpec(nodeSpec *genesis.Genesis) *Config {
Wasmer: DefaultLogLevel,
},
Account: &AccountConfig{
Key: "",
Key: defaultAccount,
Unlock: "",
},
Core: &CoreConfig{
Expand Down

0 comments on commit 000b9b4

Please sign in to comment.