-
Notifications
You must be signed in to change notification settings - Fork 2.1k
Description
Given a fully merged config, I would like to update an item based upon a path to the item.
Assume the following JSON config.
{
"id": "0001",
"type": "donut",
"name": "Cake",
"ppu": 0.55,
"batters": {
"batter": [{
"type": "Regular"
},
{
"type": "Chocolate"
},
{
"type": "Blueberry"
},
{
"type": "Devil's Food"
}
],
"topping": [
"Icing", "Chocolate"
]
}
}v := New()
v.SetConfigType("json")
v.ReadConfig(bytes.NewBuffer(jsonExample))
os.Setenv("batters.doesnotexist", "ted")
os.Setenv("batters.batter.0.type", "bob")
os.Setenv("batters.topping.1", "frosting")
v.SurgicalPathUpdateFromEnv()
os.Remove("batters.doesnotexist")
os.Remove("batters.batter.0.type")
os.Remove("batters.topping.1")should result in the following updates;
{
"id": "0001",
"type": "donut",
"name": "Cake",
"ppu": 0.55,
"batters": {
"batter": [{
"type": "bob"
},
{
"type": "Chocolate"
},
{
"type": "Blueberry"
},
{
"type": "Devil's Food"
}
],
"topping": [
"Icing", "frosting"
]
}
}Describe alternatives you've considered
reference project - viperEx
I was able to do this after the fact with the following technique
allSettings := myViper.AllSettings()
myViperEx := New("__")
myViperEx.SurgicalUpdate("nest__Eggs__0__Weight", 1234, allSettings)
myViperEx.SurgicalUpdate("nest__Eggs__0__SomeValues__1__Value", "abcd", allSettings)
myViperEx.SurgicalUpdate("nest__Eggs__0__SomeStrings__1__", "abcd", allSettings)
myViperEx.SurgicalUpdate("junk__A", "abcd", allSettings)
myViperEx.SurgicalUpdate("nest__junk", "abcd", allSettings)
settings := Settings{}
err = myViper.Unmarshal(&settings)where I wrote a ViperEx helper that updated the AllSettings that viper owns. Arguably it is really more of a mapstructure thing that traverses maps, etc. The difference is really should this be a separate project vs being part of Viper.
This type of processing is part of the asp.net core configuration builder which is very similar in design to the viper design.
So, I vote for being part of Viper.
On the viper side, the biggest issue I think is setting an item in an array. i.e.
viper.Set("a.b.1.name", "bob")This doesn't exist, but it should, especially when there is a getter that allows it.