From 8c49af0b68172903f1c8252202a92fece4a9f343 Mon Sep 17 00:00:00 2001 From: Henrique Dias Date: Sun, 20 Oct 2024 09:08:12 +0200 Subject: [PATCH] fix: environment parsing for username --- lib/config.go | 4 ++-- lib/config_test.go | 41 +++++++++++++++++++++++++++++++++++++++++ lib/user.go | 11 ++++++++++- 3 files changed, 53 insertions(+), 3 deletions(-) diff --git a/lib/config.go b/lib/config.go index 1c44715..fdc444a 100644 --- a/lib/config.go +++ b/lib/config.go @@ -160,8 +160,8 @@ func (c *Config) Validate() error { return fmt.Errorf("invalid config: %w", err) } - for _, u := range c.Users { - err := u.Validate(c.NoPassword) + for i := range c.Users { + err := c.Users[i].Validate(c.NoPassword) if err != nil { return fmt.Errorf("invalid config: %w", err) } diff --git a/lib/config_test.go b/lib/config_test.go index 79a1eab..e223019 100644 --- a/lib/config_test.go +++ b/lib/config_test.go @@ -22,6 +22,17 @@ func writeAndParseConfig(t *testing.T, content, extension string) *Config { return cfg } +func writeAndParseConfigWithError(t *testing.T, content, extension, error string) { + tmpDir := t.TempDir() + tmpFile := filepath.Join(tmpDir, "config"+extension) + + err := os.WriteFile(tmpFile, []byte(content), 0666) + require.NoError(t, err) + + _, err = ParseConfig(tmpFile, nil) + require.ErrorContains(t, err, error) +} + func TestConfigDefaults(t *testing.T) { t.Parallel() @@ -224,3 +235,33 @@ func TestConfigEnv(t *testing.T) { require.NoError(t, os.Setenv("WD_PERMISSIONS", "")) require.NoError(t, os.Setenv("WD_DIRECTORY", "")) } + +func TestConfigParseUserPasswordEnvironment(t *testing.T) { + content := ` +directory: / +users: + - username: '{env}USER1_USERNAME' + password: '{env}USER1_PASSWORD' + - username: basic + password: basic +` + + writeAndParseConfigWithError(t, content, ".yml", "username environment variable is empty") + + err := os.Setenv("USER1_USERNAME", "admin") + require.NoError(t, err) + + writeAndParseConfigWithError(t, content, ".yml", "password environment variable is empty") + + err = os.Setenv("USER1_PASSWORD", "admin") + require.NoError(t, err) + + cfg := writeAndParseConfig(t, content, ".yaml") + require.NoError(t, cfg.Validate()) + + require.Equal(t, "admin", cfg.Users[0].Username) + require.Equal(t, "basic", cfg.Users[1].Username) + + require.True(t, cfg.Users[0].checkPassword("admin")) + require.True(t, cfg.Users[1].checkPassword("basic")) +} diff --git a/lib/user.go b/lib/user.go index bc1576e..a9d4b1e 100644 --- a/lib/user.go +++ b/lib/user.go @@ -27,12 +27,21 @@ func (u User) checkPassword(input string) bool { func (u *User) Validate(noPassword bool) error { if u.Username == "" { return errors.New("invalid user: username must be set") + } else if strings.HasPrefix(u.Username, "{env}") { + env := strings.TrimPrefix(u.Username, "{env}") + if env == "" { + return fmt.Errorf("invalid user %q: username environment variable not set", u.Username) + } + + u.Username = os.Getenv(env) + if u.Username == "" { + return fmt.Errorf("invalid user %q: username environment variable is empty", u.Username) + } } if u.Password == "" && !noPassword { return fmt.Errorf("invalid user %q: password must be set", u.Username) } else if strings.HasPrefix(u.Password, "{env}") { - env := strings.TrimPrefix(u.Password, "{env}") if env == "" { return fmt.Errorf("invalid user %q: password environment variable not set", u.Username)