Go で匿名メンバーを使用してマーシャルされた JSON 構造体を平坦化する
次のコード:
<code class="go">type Anything interface{} type Hateoas struct { Anything Links map[string]string `json:"_links"` } func MarshalHateoas(subject interface{}) ([]byte, error) { h := &Hateoas{subject, make(map[string]string)} switch s := subject.(type) { case *User: h.Links["self"] = fmt.Sprintf("http://user/%d", s.Id) case *Session: h.Links["self"] = fmt.Sprintf("http://session/%d", s.Id) } return json.MarshalIndent(h, "", " ") }</code>
目標は次のとおりです。匿名メンバーがフラット化される方法で JSON をマーシャリングします。デフォルトでは、匿名メンバーは JSON 出力内の別の名前付きフィールドとして扱われます。
これに対する解決策は、reflect パッケージを使用して、シリアル化したい構造体のフィールドをマップに手動でマップすることです[文字列]インターフェイス{}。このようにして、新しいフィールドを導入することなく、元の構造体のフラットな構造を維持できます。
これを実現するコードは次のとおりです。
<code class="go">func MarshalHateoas(subject interface{}) ([]byte, error) { links := make(map[string]string) out := make(map[string]interface{}) subjectValue := reflect.Indirect(reflect.ValueOf(subject)) subjectType := subjectValue.Type() for i := 0; i < subjectType.NumField(); i++ { field := subjectType.Field(i) name := subjectType.Field(i).Name out[field.Tag.Get("json")] = subjectValue.FieldByName(name).Interface() } switch s := subject.(type) { case *User: links["self"] = fmt.Sprintf("http://user/%d", s.Id) case *Session: links["self"] = fmt.Sprintf("http://session/%d", s.Id) } out["_links"] = links return json.MarshalIndent(out, "", " ") }</code>
このコードは、構造体のフィールドを反復処理します。 、値を取得し、フィールドの JSON タグをキーとして使用して出力マップに追加します。このプロセスにより、匿名メンバーのフィールドが出力マップに確実にフラット化されます。
この方法で JSON マーシャリング プロセスをカスタマイズすることで、インターフェイスによって提供される柔軟性と型安全性を維持しながら、目的の JSON 出力を実現できます。
以上が匿名メンバーを使用して Go でマーシャルされた JSON 構造体をフラット化するにはどうすればよいですか?の詳細内容です。詳細については、PHP 中国語 Web サイトの他の関連記事を参照してください。