Rumah > pembangunan bahagian belakang > Golang > Bagaimana untuk menyahmarshal json ke dalam struct tanpa memetakan semua elemen sambil mengekalkan semua maklumat

Bagaimana untuk menyahmarshal json ke dalam struct tanpa memetakan semua elemen sambil mengekalkan semua maklumat

王林
Lepaskan: 2024-02-05 21:36:04
ke hadapan
493 orang telah melayarinya

如何将 json 解组为结构体而不映射所有元素,同时保留所有信息

Kandungan soalan

Saya menerima objek JSON daripada baris gilir. Saya mahu memproses sebahagian daripada objek dan mengemas kininya sebelum menghantar ke baris gilir lain.

Jika saya ada input

{
  "one": "data1",
  "two": "data2",
  "three": "data3",
  ...
}
Salin selepas log masuk

Saya ingin mengambil onetwo dan mengira beberapa maklumat sebelum menambah output baharu dan menghantar mesej yang serupa

{
  "one": "data1UPDATED",
  "two": "data2",
  "three": "data3",
  ...
  "extra_info": "extra"
}
Salin selepas log masuk

Untuk dapat memproses data dengan lebih baik, saya ingin membongkar JSON ke dalam struktur yang serupa

type Message struct {
 One string `json:one`
 Two string `json:two`
}
Salin selepas log masuk

Tetapi tidak mahu memetakan semua medan kerana kebanyakannya tidak berkaitan dengan aplikasi ini dan yang lain mungkin berubah.

Perkara yang saya telah cuba

Saya cuba memetakan semua medan ke json.RawMessage

type Message struct {
 One string `json:"one"`
 Two string `json:"two"`
 ExtraFields json.RawMessage `json:"-"`
}
Salin selepas log masuk

Namun, semasa menyusun struktur, medan yang terkandung dalam ExtraFields tidak disertakan.

{
  "one": "data1",
  "two": "data2"
}
Salin selepas log masuk

Saya juga cuba menulis unmarshalling tersuai yang menyimpan mesej lengkap dalam struktur, dengan mesej berguna dalam satu elemen dan maklumat lain dalam medan lain

type TmpMessage struct{
  Msg Message
  Others json.RawMessage
}
Salin selepas log masuk

Tetapi ini menjadi sangat mengelirukan dan saya mengharapkan penyelesaian yang lebih bersih.

Adakah terdapat cara untuk melakukan ini, secara alternatif tanpa unmarshaller ke dalam struct dan hanya menggunakan yang asal map[string] 接口{}的唯一选择?


Jawapan betul


Anda boleh menulis unmarshaller tersuai seperti:

https://www.php.cn/link/a73d9b34d6f7c322fa3e34c633b1297d

func (m *Message) UnmarshalJSON(data []byte) error {
  tmp := make(map[string]interface{})
  if err := json.Unmarshal(data, &tmp); err != nil {
    return err
  }
  t := reflect.TypeOf(*m)
  for i := 0; i < t.NumField(); i++ {
    f := t.Field(i)
    if f.Name != "ExtraFields" {
      jsonTag := f.Tag.Get("json")
      // this part should probably by a type switch...
      reflect.ValueOf(m).Elem().Field(i).SetString(tmp[jsonTag].(string))
      delete(tmp, jsonTag)
    }
  }
  var err error
  m.ExtraFields, err = json.Marshal(tmp)
  return err
}
Salin selepas log masuk

Atas ialah kandungan terperinci Bagaimana untuk menyahmarshal json ke dalam struct tanpa memetakan semua elemen sambil mengekalkan semua maklumat. Untuk maklumat lanjut, sila ikut artikel berkaitan lain di laman web China PHP!

sumber:stackoverflow.com
Kenyataan Laman Web ini
Kandungan artikel ini disumbangkan secara sukarela oleh netizen, dan hak cipta adalah milik pengarang asal. Laman web ini tidak memikul tanggungjawab undang-undang yang sepadan. Jika anda menemui sebarang kandungan yang disyaki plagiarisme atau pelanggaran, sila hubungi admin@php.cn
Tutorial Popular
Lagi>
Muat turun terkini
Lagi>
kesan web
Kod sumber laman web
Bahan laman web
Templat hujung hadapan