How Do I Unmarshal Dynamic Viper or JSON keys as part of struct field in go

做~自己de王妃 提交于 2019-12-31 07:08:03

问题


I find the marshaling & unMarshaling in GOLANG very confusing when JSON is not in "desired" format. For example, in a JSON config file (which I am trying to use with Viper) I have a config file that looks like :

{
  "things" :{
    "123abc" :{
      "key1": "anything",
      "key2" : "more"
    },
    "456xyz" :{
      "key1": "anything2",
      "key2" : "more2"
    },
    "blah" :{
      "key1": "anything3",
      "key2" : "more3"
    }
  }
}

where "things" could be an object in another object n levels down and I have a struct :

type Thing struct {
  Name string  `?????`
  Key1 string  `json:"key2"`
  Key2 string  `json:"key2"`
}

How to I go about unMarshalling the JSON and more specifically viper config (using viper.Get("things") to get an array of Things like:

t:= Things{
   Name: "123abc",
   Key1: "anything",
   Key2: "more",
}

I am particularly unsure how to get the key as a struct field


回答1:


Use a map for dynamic keys:

type X struct {
    Things map[string]Thing
}

type Thing struct {
    Key1 string
    Key2 string
}

Unmarshal like this:

var x X
if err := json.Unmarshal(data, &x); err != nil {
    // handle error
}

Playground Example

If the name must be a member of the struct, then write a loop to add it after unmarshal:

type Thing struct {
    Name string `json:"-"` // <-- add the field
    Key1 string
    Key2 string
}

...

// Fix the name field after unmarshal
for k, t := range x.Things {
    t.Name = k
    x.Things[k] = t
}

Playground example



来源:https://stackoverflow.com/questions/50749869/how-do-i-unmarshal-dynamic-viper-or-json-keys-as-part-of-struct-field-in-go

标签
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!