Skip to content

Commit

Permalink
feat: If not already existant, create ftl-project.toml and/or modul…
Browse files Browse the repository at this point in the history
…e config or secret (#1273)

Fixes issue #1174

Also tested manually by:
```
Open ftl-project.toml and confirm no module "echooo" is referenced
$ ftl config set --inline echooo.HILLBILLY JENKINS
Open ftl-project.toml and confirm this KV pair was added

$ rm ftl-project.toml
$ ftl config set --inline echooo.HILLBILLY JENKINS
Open ftl-project.toml and confirm this KV pair was added

Repeat for s/config/secret/
```
  • Loading branch information
deniseli authored Apr 16, 2024
1 parent 2500d32 commit cdca0a0
Show file tree
Hide file tree
Showing 5 changed files with 87 additions and 3 deletions.
2 changes: 2 additions & 0 deletions common/configuration/manager_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@ import (
"testing"

"github.com/alecthomas/assert/v2"
"github.com/alecthomas/types/optional"
"github.com/zalando/go-keyring"

"github.com/TBD54566975/ftl/internal/log"
Expand Down Expand Up @@ -54,6 +55,7 @@ func TestManager(t *testing.T) {
{Ref: Ref{Name: "baz"}, Accessor: URL("envar://baz")},
{Ref: Ref{Name: "foo"}, Accessor: URL("inline://ImJhciI")},
{Ref: Ref{Name: "mutable"}, Accessor: URL("inline://ImhlbGxvIg")},
{Ref: Ref{Module: optional.Some[string]("echo"), Name: "default"}, Accessor: URL("inline://ImFub255bW91cyI")},
})
})
}
Expand Down
14 changes: 12 additions & 2 deletions common/configuration/projectconfig_resolver.go
Original file line number Diff line number Diff line change
Expand Up @@ -101,9 +101,9 @@ func (p ProjectConfigResolver[R]) getMapping(config pc.Config, module optional.O
get := func(dest pc.ConfigAndSecrets) map[string]*pc.URL {
switch any(k).(type) {
case Configuration:
return dest.Config
return emptyMapIfNil(dest.Config)
case Secrets:
return dest.Secrets
return emptyMapIfNil(dest.Secrets)
default:
panic("unsupported kind")
}
Expand All @@ -121,6 +121,13 @@ func (p ProjectConfigResolver[R]) getMapping(config pc.Config, module optional.O
return mapping, nil
}

func emptyMapIfNil(mapping map[string]*pc.URL) map[string]*pc.URL {
if mapping == nil {
return map[string]*pc.URL{}
}
return mapping
}

func (p ProjectConfigResolver[R]) setMapping(config pc.Config, module optional.Option[string], mapping map[string]*pc.URL) error {
var k R
set := func(dest *pc.ConfigAndSecrets, mapping map[string]*pc.URL) {
Expand All @@ -143,5 +150,8 @@ func (p ProjectConfigResolver[R]) setMapping(config pc.Config, module optional.O
set(&config.Global, mapping)
}
configPaths := pc.ConfigPaths(p.Config)
if len(configPaths) == 0 {
return pc.Save(pc.GetDefaultConfigPath(), config)
}
return pc.Save(configPaths[len(configPaths)-1], config)
}
63 changes: 63 additions & 0 deletions common/configuration/projectconfig_resolver_test.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,63 @@
package configuration

import (
"context"
"net/url"
"os"
"path/filepath"
"testing"

"github.com/alecthomas/assert/v2"
"github.com/alecthomas/types/optional"

"github.com/TBD54566975/ftl/common/projectconfig"
"github.com/TBD54566975/ftl/internal/log"
)

func TestSet(t *testing.T) {
defaultPath := projectconfig.GetDefaultConfigPath()
origConfigBytes, err := os.ReadFile(defaultPath)
assert.NoError(t, err)

config := filepath.Join(t.TempDir(), "ftl-project.toml")
existing, err := os.ReadFile("testdata/ftl-project.toml")
assert.NoError(t, err)
err = os.WriteFile(config, existing, 0600)
assert.NoError(t, err)

t.Run("ExistingModule", func(t *testing.T) {
setAndAssert(t, "echo", []string{config})
})
t.Run("NewModule", func(t *testing.T) {
setAndAssert(t, "echooo", []string{config})
})
t.Run("MissingTOMLFile", func(t *testing.T) {
err := os.Remove(config)
assert.NoError(t, err)
setAndAssert(t, "echooooo", []string{})
err = os.WriteFile(defaultPath, origConfigBytes, 0600)
assert.NoError(t, err)
})
}

func setAndAssert(t *testing.T, module string, config []string) {
t.Helper()

ctx := log.ContextWithNewDefaultLogger(context.Background())

cf, err := New(ctx,
ProjectConfigResolver[Configuration]{Config: config},
[]Provider[Configuration]{
EnvarProvider[Configuration]{},
InlineProvider[Configuration]{Inline: true}, // Writer
})
assert.NoError(t, err)

var got *url.URL
want := URL("inline://asdfasdf")
err = cf.Set(ctx, Ref{Module: optional.Some[string](module), Name: "default"}, want)
assert.NoError(t, err)
err = cf.Get(ctx, Ref{Module: optional.Some[string](module), Name: "default"}, &got)
assert.NoError(t, err)
assert.Equal(t, want, got)
}
5 changes: 5 additions & 0 deletions common/configuration/testdata/ftl-project.toml
Original file line number Diff line number Diff line change
Expand Up @@ -8,3 +8,8 @@ mutable = "keychain://mutable"
baz = "envar://baz"
foo = "inline://ImJhciI"
mutable = "inline://ImhlbGxvIg"

[modules]
[modules.echo]
[modules.echo.configuration]
default = "inline://ImFub255bW91cyI"
6 changes: 5 additions & 1 deletion common/projectconfig/projectconfig.go
Original file line number Diff line number Diff line change
Expand Up @@ -42,14 +42,18 @@ func ConfigPaths(input []string) []string {
if len(input) > 0 {
return input
}
path := filepath.Join(internal.GitRoot(""), "ftl-project.toml")
path := GetDefaultConfigPath()
_, err := os.Stat(path)
if err == nil {
return []string{path}
}
return []string{}
}

func GetDefaultConfigPath() string {
return filepath.Join(internal.GitRoot(""), "ftl-project.toml")
}

func LoadConfig(ctx context.Context, input []string) (Config, error) {
logger := log.FromContext(ctx)
configPaths := ConfigPaths(input)
Expand Down

0 comments on commit cdca0a0

Please sign in to comment.