UnmarshalJSON Implementation for Derived Scalars in Go
Problem:
A custom type that converts subtyped integer constants to strings and vice versa requires automatic unmarshalling of JSON strings. This is challenging because UnmarshalJSON does not provide a way to modify the scalar value without using a struct.
Solution:
To implement UnmarshalJSON for a derived scalar type, consider the following steps:
Use a Pointer Receiver:
Use a pointer receiver for the UnmarshalJSON method to modify the value of the receiver.
Unmarshal to a String:
Unmarshal the JSON text into a plain string, removing all JSON quoting.
Lookup and Set Value:
Use the Lookup function to retrieve the corresponding PersonID based on the string value. Assign the result to the receiver.
Example:
func (intValue *PersonID) UnmarshalJSON(data []byte) error { var s string if err := json.Unmarshal(data, &s); err != nil { return err } *intValue = Lookup(s) return nil }
Code Example:
package main import ( "encoding/json" "fmt" ) type PersonID int const ( Bob PersonID = iota Jane Ralph Nobody = -1 ) var nameMap = map[string]PersonID{ "Bob": Bob, "Jane": Jane, "Ralph": Ralph, "Nobody": Nobody, } var idMap = map[PersonID]string{ Bob: "Bob", Jane: "Jane", Ralph: "Ralph", Nobody: "Nobody", } func (intValue PersonID) Name() string { return idMap[intValue] } func Lookup(name string) PersonID { return nameMap[name] } func (intValue *PersonID) UnmarshalJSON(data []byte) error { var s string if err := json.Unmarshal(data, &s); err != nil { return err } *intValue = Lookup(s) return nil } type MyType struct { Person PersonID `json: "person"` Count int `json: "count"` Greeting string `json: "greeting"` } func main() { var m MyType if err := json.Unmarshal([]byte(`{"person": "Ralph", "count": 4, "greeting": "Hello"}`), &m); err != nil { fmt.Println(err) } else { for i := 0; iOutput:
Hello Ralph Hello Ralph Hello Ralph Hello Ralph
Disclaimer: All resources provided are partly from the Internet. If there is any infringement of your copyright or other rights and interests, please explain the detailed reasons and provide proof of copyright or rights and interests and then send it to the email: [email protected] We will handle it for you as soon as possible.
Copyright© 2022 湘ICP备2022001581号-3