Je veux analyser un objet JSON dans Go, mais je veux spécifier des valeurs par défaut pour les champs qui ne sont pas donnés. Par exemple, j'ai le type struct:
type Test struct {
A string
B string
C string
}
Les valeurs par défaut pour A, B et C sont respectivement "a", "b" et "c". Cela signifie que lorsque j'analyse le json:
{"A": "1", "C": 3}
Je veux obtenir la structure:
Test{A: "1", B: "b", C: "3"}
Est-ce possible en utilisant le package intégré encoding/json
? Sinon, existe-t-il une bibliothèque Go dotée de cette fonctionnalité?
Ceci est possible en utilisant l'encodage/json: lorsque vous appelez json.Unmarshal
, Vous n'avez pas besoin de lui donner une structure vide, vous pouvez lui en donner une avec des valeurs par défaut.
Pour votre exemple:
var example []byte = []byte(`{"A": "1", "C": "3"}`)
out := Test{
A: "default a",
B: "default b",
// default for C will be "", the empty value for a string
}
err := json.Unmarshal(example, &out) // <--
if err != nil {
panic(err)
}
fmt.Printf("%+v", out)
Courir cet exemple dans la cour de récréation Go renvoie {A:1 B:default b C:3}
.
Comme vous pouvez le voir, json.Unmarshal(example, &out)
démasque le JSON en out
, écrasant les valeurs spécifiées dans le JSON, mais laissant les autres champs inchangés.
Dans le cas où vous avez une liste ou une carte des structures Test
, la réponse acceptée n'est plus possible mais elle peut facilement être étendue avec une méthode UnmarshalJSON:
func (t *Test) UnmarshalJSON(data []byte) error {
type testAlias Test
test := &testAlias{
B: "default B",
}
_ = json.Unmarshal(data, test)
*t = Test(*test)
return nil
}
Le testAlias est nécessaire pour empêcher les appels récursifs à UnmarshalJSON. Cela fonctionne car un nouveau type n'a aucune méthode définie.