map.go 1.1 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344
  1. // Copyright 2020 Jebbs. All rights reserved.
  2. // Use of this source code is governed by MIT
  3. // license that can be found in the LICENSE file.
  4. package merge
  5. import (
  6. "fmt"
  7. "reflect"
  8. )
  9. // mergeMaps merges source map into target
  10. // it supports only map[string]interface{} type for any children of the map tree
  11. func mergeMaps(target map[string]interface{}, source map[string]interface{}) (err error) {
  12. for key, value := range source {
  13. target[key], err = mergeField(target[key], value)
  14. if err != nil {
  15. return
  16. }
  17. }
  18. return
  19. }
  20. func mergeField(target interface{}, source interface{}) (interface{}, error) {
  21. if source == nil {
  22. return target, nil
  23. }
  24. if target == nil {
  25. return source, nil
  26. }
  27. if reflect.TypeOf(source) != reflect.TypeOf(target) {
  28. return nil, fmt.Errorf("type mismatch, expect %T, incoming %T", target, source)
  29. }
  30. if slice, ok := source.([]interface{}); ok {
  31. tslice, _ := target.([]interface{})
  32. tslice = append(tslice, slice...)
  33. return tslice, nil
  34. } else if smap, ok := source.(map[string]interface{}); ok {
  35. tmap, _ := target.(map[string]interface{})
  36. err := mergeMaps(tmap, smap)
  37. return tmap, err
  38. }
  39. return source, nil
  40. }