Skip to content

Commit

Permalink
Merge pull request #59 from blockassets/conf-issues
Browse files Browse the repository at this point in the history
recursively merge json objects instead of just merging keys
  • Loading branch information
lookfirst authored Mar 20, 2018
2 parents 87ae8e0 + dcdc911 commit a20dc61
Show file tree
Hide file tree
Showing 2 changed files with 82 additions and 5 deletions.
47 changes: 47 additions & 0 deletions service/agent/config_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,26 @@ const priorConfigVersion = `{
}
`

const failingConfig = `
{
"cmdLine": {
"port": ":1111"
},
"controller": {
"reboot": {
"delay": "5s"
}
},
"monitor": {
"load": {
"period_secs": 60,
"high_load_Mark": 5,
"enabled": true
}
}
}
`

func defaultConfig() []byte {
data, _ := ioutil.ReadFile("../../conf/bam_agent.json")
return data
Expand Down Expand Up @@ -72,6 +92,33 @@ func TestNewConfig(t *testing.T) {
}
}

func TestLoadingOldConfig(t *testing.T) {
file, err := ioutil.TempFile("", "agent-config")
defer os.Remove(file.Name())

// Write out an old version of a file
ioutil.WriteFile(file.Name(), []byte(failingConfig), 644)
file.Close()

if err != nil {
t.Fatal(err)
}

cfg := NewConfig(tool.CmdLine{
AgentConfigPath: file.Name(),
}, defaultConfig())

if !cfg.Loaded().Monitor.HighLoad.Enabled {
t.Fatalf("expected highLoad to be enabled")
}

// We should have saved the file as part of the load
fileData, err := ioutil.ReadFile(file.Name())
if !strings.Contains(string(fileData), "highLoad") {
t.Fatalf("expected file data to have updated port number")
}
}

// simulate a BAM agent binary update that adds a structure to the default BAM interface
// by saving a previous config file that doesnt have the current monitors in it
func TestStructChangeToConfig(t *testing.T) {
Expand Down
40 changes: 35 additions & 5 deletions tool/json.go
Original file line number Diff line number Diff line change
Expand Up @@ -89,17 +89,47 @@ func getRandomizedDuration(duration time.Duration) time.Duration {
}

/*
Merges source into/over destination
Recursively merges source into/over destination
*/
func Merge(src []byte, dst []byte) ([]byte, error) {
var mergeMap map[string]interface{}
err := jsoniter.Unmarshal(dst, &mergeMap)
var err error

var srcObj interface{}
err = jsoniter.Unmarshal(src, &srcObj)
if err != nil {
return nil, err
}
err = jsoniter.Unmarshal(src, &mergeMap)

var dstObj interface{}
err = jsoniter.Unmarshal(dst, &dstObj)
if err != nil {
return nil, err
}
return jsoniter.Marshal(mergeMap)

return jsoniter.Marshal(merge1(srcObj, dstObj))
}

// https://play.golang.org/p/8jlJUbEJKf
func merge1(x1, x2 interface{}) interface{} {
switch x1 := x1.(type) {
case map[string]interface{}:
x2, ok := x2.(map[string]interface{})
if !ok {
return x1
}
for k, v2 := range x2 {
if v1, ok := x1[k]; ok {
x1[k] = merge1(v1, v2)
} else {
x1[k] = v2
}
}
case nil:
// merge(nil, map[string]interface{...}) -> map[string]interface{...}
x2, ok := x2.(map[string]interface{})
if ok {
return x2
}
}
return x1
}

0 comments on commit a20dc61

Please sign in to comment.