Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
27 changes: 27 additions & 0 deletions internal/config/config.go
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@ import (
"fmt"
"os"
"path/filepath"
"sort"
"strings"

"github.com/gleanwork/glean-cli/internal/debug"
Expand Down Expand Up @@ -284,6 +285,28 @@ func loadFromKeyring() *Config {
return cfg
}

var knownConfigKeys = map[string]bool{
"host": true,
"token": true,
"oauth_client_id": true,
"oauth_client_secret": true,
}

func validateConfigKeys(data []byte) []string {
var raw map[string]json.RawMessage
if err := json.Unmarshal(data, &raw); err != nil {
return nil
}
var warnings []string
for key := range raw {
if !knownConfigKeys[key] {
warnings = append(warnings, fmt.Sprintf("unknown key %q in config.json (typo?)", key))
}
}
sort.Strings(warnings)
return warnings
}

func loadFromFile() (*Config, error) {
if ConfigPath == "" {
return nil, fmt.Errorf("config path not set")
Expand All @@ -299,6 +322,10 @@ func loadFromFile() (*Config, error) {
}
cfgLog.Log("loaded config file: %s (%d bytes)", ConfigPath, len(data))

for _, w := range validateConfigKeys(data) {
cfgLog.Log("%s", w)
}

var cfg Config
if err := json.Unmarshal(data, &cfg); err != nil {
return nil, fmt.Errorf("error parsing config file: %w", err)
Expand Down
35 changes: 35 additions & 0 deletions internal/config/config_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -374,6 +374,41 @@ func TestSaveHostToFile_DoesNotTouchKeyring(t *testing.T) {
assert.Empty(t, cfg.GleanToken)
}

func TestValidateConfigKeys(t *testing.T) {
t.Run("unknown key produces warning", func(t *testing.T) {
data := []byte(`{"host":"x.glean.com","toke":"bad"}`)
warnings := validateConfigKeys(data)
require.Len(t, warnings, 1)
assert.Contains(t, warnings[0], `unknown key "toke"`)
})

t.Run("all known keys produce no warnings", func(t *testing.T) {
data := []byte(`{"host":"x","token":"t","oauth_client_id":"id","oauth_client_secret":"s"}`)
warnings := validateConfigKeys(data)
assert.Empty(t, warnings)
})

t.Run("unknown keys do not prevent loading", func(t *testing.T) {
isolateAuthState(t)

cfgData := []byte(`{"host":"test-be.glean.com","token":"tok","extra_field":"val"}`)
err := os.MkdirAll(filepath.Dir(ConfigPath), 0700)
require.NoError(t, err)
err = os.WriteFile(ConfigPath, cfgData, 0600)
require.NoError(t, err)

cfg, err := loadFromFile()
require.NoError(t, err)
assert.Equal(t, "test-be.glean.com", cfg.GleanHost)
assert.Equal(t, "tok", cfg.GleanToken)
})

t.Run("invalid JSON returns no warnings", func(t *testing.T) {
warnings := validateConfigKeys([]byte(`not json`))
assert.Nil(t, warnings)
})
}

func TestLoadFromFile(t *testing.T) {
_, cleanup := setupTestConfig(t)
defer cleanup()
Expand Down
Loading