c354d5f21134b5cfa65c5fc6b6b9ff0dcf691bd2

Author
Kendall Tauser <16072686+fire833@users.noreply.github.com>
Committer
GitHub <noreply@github.com>
Date

Message

feat: optionally pull config from a custom file (envvar), default to data path. (#557)

* feat: optionally pull config from a custom file (envvar), default to data path.

* docs: add docs on SOFT_SERVE_CONFIG_LOCATION

* feat: add tests for SOFT_SERVE_CONFIG_LOCATION

Diff

 1diff --git a/README.md b/README.md
 2index 9f9cf2c2557844e26de1046747d4b049cb772500..cbefcd78454a8727921dd3365f298e54026f3724 100644
 3--- a/README.md
 4+++ b/README.md
 5@@ -108,6 +108,11 @@ Make sure `git` is installed, then run `soft serve`. That’s it.
 6 This will create a `data` directory that will store all the repos, ssh keys,
 7 and database.
 8 
 9+By default, program configuration is stored within the `data` directory. But,
10+this can be overridden by setting a custom path to a config file with `SOFT_SERVE_CONFIG_LOCATION`
11+that is pre-created. If a config file pointed to by `SOFT_SERVE_CONFIG_LOCATION`, 
12+the default location within the `data` dir is used for generating a default config.
13+
14 To change the default data path use `SOFT_SERVE_DATA_PATH` environment variable.
15 
16 ```sh
17diff --git a/pkg/config/config.go b/pkg/config/config.go
18index 103598a66972e006245046052a62a8acbd9a51da..2b650984c2d401f12c579fa702f32c7828ae5841 100644
19--- a/pkg/config/config.go
20+++ b/pkg/config/config.go
21@@ -291,6 +291,12 @@ func DefaultDataPath() string {
22 
23 // ConfigPath returns the path to the config file.
24 func (c *Config) ConfigPath() string { // nolint:revive
25+	// If we have a custom config location set, then use that.
26+	if path := os.Getenv("SOFT_SERVE_CONFIG_LOCATION"); exist(path) {
27+		return path
28+	}
29+
30+	// Otherwise, look in the data path.
31 	return filepath.Join(c.DataPath, "config.yaml")
32 }
33 
34@@ -301,7 +307,7 @@ func exist(path string) bool {
35 
36 // Exist returns true if the config file exists.
37 func (c *Config) Exist() bool {
38-	return exist(filepath.Join(c.DataPath, "config.yaml"))
39+	return exist(c.ConfigPath())
40 }
41 
42 // DefaultConfig returns the default Config. All the path values are relative
43diff --git a/pkg/config/config_test.go b/pkg/config/config_test.go
44index 503e4de49e349a1464433c76ed138a069ec9df6b..8b84ed8222ba39ca5ad4d1236f5c787b19b0ab00 100644
45--- a/pkg/config/config_test.go
46+++ b/pkg/config/config_test.go
47@@ -56,3 +56,26 @@ func TestValidateInitAdminKeys(t *testing.T) {
48 		"ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAINMwLvyV3ouVrTysUYGoJdl5Vgn5BACKov+n9PlzfPwH",
49 	})
50 }
51+
52+func TestCustomConfigLocation(t *testing.T) {
53+	is := is.New(t)
54+	td := t.TempDir()
55+	t.Cleanup(func() {
56+		is.NoErr(os.Unsetenv("SOFT_SERVE_CONFIG_LOCATION"))
57+	})
58+
59+	// Test that we get data from the custom file location, and not from the data dir.
60+	is.NoErr(os.Setenv("SOFT_SERVE_CONFIG_LOCATION", "testdata/config.yaml"))
61+	is.NoErr(os.Setenv("SOFT_SERVE_DATA_PATH", td))
62+	cfg := DefaultConfig()
63+	is.NoErr(cfg.Parse())
64+	is.Equal(cfg.Name, "Test server name")
65+	// If we unset the custom location, then use the default location.
66+	is.NoErr(os.Unsetenv("SOFT_SERVE_CONFIG_LOCATION"))
67+	cfg = DefaultConfig()
68+	is.Equal(cfg.Name, "Soft Serve")
69+	// Test that if the custom config location doesn't exist, default to datapath config.
70+	is.NoErr(os.Setenv("SOFT_SERVE_CONFIG_LOCATION", "testdata/config_nonexistent.yaml"))
71+	cfg = DefaultConfig()
72+	is.Equal(cfg.Name, "Soft Serve")
73+}
74diff --git a/pkg/config/testdata/config.yaml b/pkg/config/testdata/config.yaml
75new file mode 100644
76index 0000000000000000000000000000000000000000..838b4c3c7678379d7f620bb663efa810f62675a7
77--- /dev/null
78+++ b/pkg/config/testdata/config.yaml
79@@ -0,0 +1,3 @@
80+# Soft Serve Server configurations
81+
82+name: "Test server name"