mirror of https://github.com/spf13/viper.git
parent
13df721090
commit
8dfc4784be
37
viper.go
37
viper.go
|
@ -191,7 +191,10 @@ type Viper struct {
|
||||||
|
|
||||||
// Name of file to look for inside the path
|
// Name of file to look for inside the path
|
||||||
configName string
|
configName string
|
||||||
configFile string
|
configFile struct {
|
||||||
|
path string
|
||||||
|
explicitlySet bool
|
||||||
|
}
|
||||||
configType string
|
configType string
|
||||||
configPermissions os.FileMode
|
configPermissions os.FileMode
|
||||||
envPrefix string
|
envPrefix string
|
||||||
|
@ -411,7 +414,8 @@ func (v *Viper) WatchConfig() {
|
||||||
func SetConfigFile(in string) { v.SetConfigFile(in) }
|
func SetConfigFile(in string) { v.SetConfigFile(in) }
|
||||||
func (v *Viper) SetConfigFile(in string) {
|
func (v *Viper) SetConfigFile(in string) {
|
||||||
if in != "" {
|
if in != "" {
|
||||||
v.configFile = in
|
v.configFile.path = in
|
||||||
|
v.configFile.explicitlySet = true
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -460,7 +464,7 @@ func (v *Viper) getEnv(key string) (string, bool) {
|
||||||
|
|
||||||
// ConfigFileUsed returns the file used to populate the config registry.
|
// ConfigFileUsed returns the file used to populate the config registry.
|
||||||
func ConfigFileUsed() string { return v.ConfigFileUsed() }
|
func ConfigFileUsed() string { return v.ConfigFileUsed() }
|
||||||
func (v *Viper) ConfigFileUsed() string { return v.configFile }
|
func (v *Viper) ConfigFileUsed() string { return v.configFile.path }
|
||||||
|
|
||||||
// AddConfigPath adds a path for Viper to search for the config file in.
|
// AddConfigPath adds a path for Viper to search for the config file in.
|
||||||
// Can be called multiple times to define multiple search paths.
|
// Can be called multiple times to define multiple search paths.
|
||||||
|
@ -1407,20 +1411,32 @@ func (v *Viper) MergeConfigMap(cfg map[string]interface{}) error {
|
||||||
// WriteConfig writes the current configuration to a file.
|
// WriteConfig writes the current configuration to a file.
|
||||||
func WriteConfig() error { return v.WriteConfig() }
|
func WriteConfig() error { return v.WriteConfig() }
|
||||||
func (v *Viper) WriteConfig() error {
|
func (v *Viper) WriteConfig() error {
|
||||||
filename, err := v.getConfigFile()
|
if !v.configFile.explicitlySet {
|
||||||
|
_, err := v.getConfigFile()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
|
if _, ok := err.(ConfigFileNotFoundError); ok {
|
||||||
|
if len(v.configPaths) < 1 {
|
||||||
|
return errors.New("missing configuration for 'configPath'")
|
||||||
|
}
|
||||||
|
v.configFile.path = filepath.Join(v.configPaths[0], v.configName+"."+v.configType)
|
||||||
|
} else {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
return v.writeConfig(filename, true)
|
}
|
||||||
|
}
|
||||||
|
return v.WriteConfigAs(v.configFile.path)
|
||||||
}
|
}
|
||||||
|
|
||||||
// SafeWriteConfig writes current configuration to file only if the file does not exist.
|
// SafeWriteConfig writes current configuration to file only if the file does not exist.
|
||||||
func SafeWriteConfig() error { return v.SafeWriteConfig() }
|
func SafeWriteConfig() error { return v.SafeWriteConfig() }
|
||||||
func (v *Viper) SafeWriteConfig() error {
|
func (v *Viper) SafeWriteConfig() error {
|
||||||
|
if !v.configFile.explicitlySet {
|
||||||
if len(v.configPaths) < 1 {
|
if len(v.configPaths) < 1 {
|
||||||
return errors.New("missing configuration for 'configPath'")
|
return errors.New("missing configuration for 'configPath'")
|
||||||
}
|
}
|
||||||
return v.SafeWriteConfigAs(filepath.Join(v.configPaths[0], v.configName+"."+v.configType))
|
v.configFile.path = filepath.Join(v.configPaths[0], v.configName+"."+v.configType)
|
||||||
|
}
|
||||||
|
return v.SafeWriteConfigAs(v.configFile.path)
|
||||||
}
|
}
|
||||||
|
|
||||||
// WriteConfigAs writes current configuration to a given filename.
|
// WriteConfigAs writes current configuration to a given filename.
|
||||||
|
@ -1947,7 +1963,8 @@ func SetConfigName(in string) { v.SetConfigName(in) }
|
||||||
func (v *Viper) SetConfigName(in string) {
|
func (v *Viper) SetConfigName(in string) {
|
||||||
if in != "" {
|
if in != "" {
|
||||||
v.configName = in
|
v.configName = in
|
||||||
v.configFile = ""
|
v.configFile.path = ""
|
||||||
|
v.configFile.explicitlySet = false
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1986,14 +2003,14 @@ func (v *Viper) getConfigType() string {
|
||||||
}
|
}
|
||||||
|
|
||||||
func (v *Viper) getConfigFile() (string, error) {
|
func (v *Viper) getConfigFile() (string, error) {
|
||||||
if v.configFile == "" {
|
if v.configFile.path == "" {
|
||||||
cf, err := v.findConfigFile()
|
cf, err := v.findConfigFile()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return "", err
|
return "", err
|
||||||
}
|
}
|
||||||
v.configFile = cf
|
v.configFile.path = cf
|
||||||
}
|
}
|
||||||
return v.configFile, nil
|
return v.configFile.path, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (v *Viper) searchInPath(in string) (filename string) {
|
func (v *Viper) searchInPath(in string) (filename string) {
|
||||||
|
|
|
@ -1372,7 +1372,7 @@ hobbies:
|
||||||
name: steve
|
name: steve
|
||||||
`)
|
`)
|
||||||
|
|
||||||
func TestWriteConfig(t *testing.T) {
|
func TestWriteConfigAs(t *testing.T) {
|
||||||
fs := afero.NewMemMapFs()
|
fs := afero.NewMemMapFs()
|
||||||
testCases := map[string]struct {
|
testCases := map[string]struct {
|
||||||
configName string
|
configName string
|
||||||
|
@ -1495,7 +1495,7 @@ func TestWriteConfig(t *testing.T) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func TestWriteConfigTOML(t *testing.T) {
|
func TestWriteConfigAsTOML(t *testing.T) {
|
||||||
fs := afero.NewMemMapFs()
|
fs := afero.NewMemMapFs()
|
||||||
|
|
||||||
testCases := map[string]struct {
|
testCases := map[string]struct {
|
||||||
|
@ -1551,7 +1551,7 @@ func TestWriteConfigTOML(t *testing.T) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func TestWriteConfigDotEnv(t *testing.T) {
|
func TestWriteConfigAsDotEnv(t *testing.T) {
|
||||||
fs := afero.NewMemMapFs()
|
fs := afero.NewMemMapFs()
|
||||||
testCases := map[string]struct {
|
testCases := map[string]struct {
|
||||||
configName string
|
configName string
|
||||||
|
@ -1605,6 +1605,56 @@ func TestWriteConfigDotEnv(t *testing.T) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func TestWriteConfig(t *testing.T) {
|
||||||
|
v := New()
|
||||||
|
fs := afero.NewMemMapFs()
|
||||||
|
v.SetFs(fs)
|
||||||
|
v.AddConfigPath("/test")
|
||||||
|
v.SetConfigName("c")
|
||||||
|
v.SetConfigType("yaml")
|
||||||
|
require.NoError(t, v.ReadConfig(bytes.NewBuffer(yamlExample)))
|
||||||
|
require.NoError(t, v.WriteConfig())
|
||||||
|
read, err := afero.ReadFile(fs, "/test/c.yaml")
|
||||||
|
require.NoError(t, err)
|
||||||
|
assert.Equal(t, yamlWriteExpected, read)
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestWriteConfigWithExplicitlySetFile(t *testing.T) {
|
||||||
|
v := New()
|
||||||
|
fs := afero.NewMemMapFs()
|
||||||
|
v.SetFs(fs)
|
||||||
|
v.AddConfigPath("/test1")
|
||||||
|
v.SetConfigName("c1")
|
||||||
|
v.SetConfigType("yaml")
|
||||||
|
v.SetConfigFile("/test2/c2.yaml")
|
||||||
|
require.NoError(t, v.ReadConfig(bytes.NewBuffer(yamlExample)))
|
||||||
|
require.NoError(t, v.WriteConfig())
|
||||||
|
read, err := afero.ReadFile(fs, "/test2/c2.yaml")
|
||||||
|
require.NoError(t, err)
|
||||||
|
assert.Equal(t, yamlWriteExpected, read)
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestWriteConfigWithMissingConfigPath(t *testing.T) {
|
||||||
|
v := New()
|
||||||
|
fs := afero.NewMemMapFs()
|
||||||
|
v.SetFs(fs)
|
||||||
|
v.SetConfigName("c")
|
||||||
|
v.SetConfigType("yaml")
|
||||||
|
require.EqualError(t, v.WriteConfig(), "missing configuration for 'configPath'")
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestWriteConfigWithExistingFile(t *testing.T) {
|
||||||
|
v := New()
|
||||||
|
fs := afero.NewMemMapFs()
|
||||||
|
fs.Create("/test/c.yaml")
|
||||||
|
v.SetFs(fs)
|
||||||
|
v.AddConfigPath("/test")
|
||||||
|
v.SetConfigName("c")
|
||||||
|
v.SetConfigType("yaml")
|
||||||
|
err := v.WriteConfig()
|
||||||
|
require.NoError(t, err)
|
||||||
|
}
|
||||||
|
|
||||||
func TestSafeWriteConfig(t *testing.T) {
|
func TestSafeWriteConfig(t *testing.T) {
|
||||||
v := New()
|
v := New()
|
||||||
fs := afero.NewMemMapFs()
|
fs := afero.NewMemMapFs()
|
||||||
|
@ -1619,6 +1669,21 @@ func TestSafeWriteConfig(t *testing.T) {
|
||||||
assert.Equal(t, yamlWriteExpected, read)
|
assert.Equal(t, yamlWriteExpected, read)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func TestSafeWriteConfigWithExplicitlySetFile(t *testing.T) {
|
||||||
|
v := New()
|
||||||
|
fs := afero.NewMemMapFs()
|
||||||
|
v.SetFs(fs)
|
||||||
|
v.AddConfigPath("/test1")
|
||||||
|
v.SetConfigName("c1")
|
||||||
|
v.SetConfigType("yaml")
|
||||||
|
v.SetConfigFile("/test2/c2.yaml")
|
||||||
|
require.NoError(t, v.ReadConfig(bytes.NewBuffer(yamlExample)))
|
||||||
|
require.NoError(t, v.SafeWriteConfig())
|
||||||
|
read, err := afero.ReadFile(fs, "/test2/c2.yaml")
|
||||||
|
require.NoError(t, err)
|
||||||
|
assert.Equal(t, yamlWriteExpected, read)
|
||||||
|
}
|
||||||
|
|
||||||
func TestSafeWriteConfigWithMissingConfigPath(t *testing.T) {
|
func TestSafeWriteConfigWithMissingConfigPath(t *testing.T) {
|
||||||
v := New()
|
v := New()
|
||||||
fs := afero.NewMemMapFs()
|
fs := afero.NewMemMapFs()
|
||||||
|
@ -1642,7 +1707,7 @@ func TestSafeWriteConfigWithExistingFile(t *testing.T) {
|
||||||
assert.True(t, ok, "Expected ConfigFileAlreadyExistsError")
|
assert.True(t, ok, "Expected ConfigFileAlreadyExistsError")
|
||||||
}
|
}
|
||||||
|
|
||||||
func TestSafeWriteAsConfig(t *testing.T) {
|
func TestSafeWriteConfigAs(t *testing.T) {
|
||||||
v := New()
|
v := New()
|
||||||
fs := afero.NewMemMapFs()
|
fs := afero.NewMemMapFs()
|
||||||
v.SetFs(fs)
|
v.SetFs(fs)
|
||||||
|
|
Loading…
Reference in New Issue