Maison > développement back-end > Golang > Comment marshaler correctement JSON() pour les structures intégrées avec un marshaling personnalisé ?

Comment marshaler correctement JSON() pour les structures intégrées avec un marshaling personnalisé ?

Linda Hamilton
Libérer: 2024-12-07 10:40:16
original
810 Les gens l'ont consulté

How to Correctly MarshalJSON() for Embedded Structs with Custom Marshaling?

Manière idiomatique d'intégrer une structure avec la méthode MarshalJSON() personnalisée

Problème :

Comment pouvons-nous encoder une structure avec une structure intégrée qui a une méthode MarshalJSON() personnalisée ? Le résultat attendu est de préserver le marshaling personnalisé de la structure intégrée tout en codant également les champs de la structure externe.

Exemple :

type Person struct {
    Name string `json:"name"`
}

type Employee struct {
    *Person
    JobRole string `json:"jobRole"`
}
Copier après la connexion

Lorsque la personne intégrée struct a une méthode MarshalJSON() personnalisée :

func (p *Person) MarshalJSON() ([]byte, error) {
    return json.Marshal(struct {
        Name string `json:"name"`
    }{
        Name: strings.ToUpper(p.Name),
    })
}
Copier après la connexion

Le marshalage d'une instance d'employé s'interrompt, ce qui entraîne dans :

{"name": "BOB"}
Copier après la connexion

Solution :

Au lieu d'implémenter MarshalJSON() sur Person, créez un nouveau type Name qui implémente MarshalJSON(). Ensuite, modifiez Person pour utiliser ce type de nom :

type Name string

func (n Name) MarshalJSON() ([]byte, error) {
    return json.Marshal(struct {
        Name string `json:"name"`
    }{
        Name: strings.ToUpper(string(n)),
    })
}

type Person struct {
    Name Name `json:"name"`
}
Copier après la connexion

Cela permet d'appliquer la logique de marshaling personnalisée au champ Nom tout en continuant à encoder les champs Employé comme prévu.

Solution générique :

Pour une solution plus générique, implémentez MarshalJSON() sur la structure externe. Alors que les méthodes du type interne sont promues au type externe, le type externe peut ensuite regrouper le résultat dans une structure générique telle que map[string]interface{} et ajouter ses propres champs.

Exemple :

type Person struct {
    Name string `json:"name"`
}

type Employee struct {
    *Person
    JobRole string `json:"jobRole"`
}

func (e *Employee) MarshalJSON() ([]byte, error) {
    b, err := e.Person.MarshalJSON()
    if err != nil {
        return nil, err
    }

    var m map[string]interface{}
    if err := json.Unmarshal(b, &m); err != nil {
        return nil, err
    }

    m["jobRole"] = e.JobRole
    return json.Marshal(m)
}
Copier après la connexion

Ce qui précède est le contenu détaillé de. pour plus d'informations, suivez d'autres articles connexes sur le site Web de PHP en chinois!

source:php.cn
Déclaration de ce site Web
Le contenu de cet article est volontairement contribué par les internautes et les droits d'auteur appartiennent à l'auteur original. Ce site n'assume aucune responsabilité légale correspondante. Si vous trouvez un contenu suspecté de plagiat ou de contrefaçon, veuillez contacter admin@php.cn
Derniers articles par auteur
Tutoriels populaires
Plus>
Derniers téléchargements
Plus>
effets Web
Code source du site Web
Matériel du site Web
Modèle frontal