One.
You don’t have to json.Unmarshal
into an empty struct. I learned with examples like this:
type Post struct {
FavoriteCount int `json:"favorite_count"`
ID string `json:"id"`
FullText string `json:"full_text"`
}
exampleJSON := []byte(`{
"id": "098a9df8a90d8fad",
"full_text": "Blah blah blah."
}`)
var post Post
err := json.Unmarshal(exampleJSON, &post)
if err != nil {
fmt.Println(err)
}
Code language: Go (go)
There, post
is totally defaults, meaning because favorite_count
was missing in the JSON data, post.FavoriteCount
defaults to 0, the Go default value for an int
. But it doesn’t have to start that way! You can Unmarshal it into a variable of that type that isn’t all default values.
post := Post{ FavoriteCount: 5, } err = json.Unmarshal(exampleJSON, &post) if err != nil { fmt.Println(err) }
Now even though the JSON data is still missing favorite_count
, the post.FavoriteCount
value will be 5
. Useful!
And surprising to me, as a language that doesn’t have much in the way of convience methods. Like there certainly is no ...spread
like JavaScript, and this feels a smidge like spreading.
Another thing I need to learn is how to deal better with Unmarshaling data into a struct where the JSON data could be wrong. With the default json.Unmarshal
it just totally fails, and so far I’ve worked around it with really permissive temporary type
s that use a bunch of interface{}
shit and coercing it later. But I’d rather use a strict type and deal with it on the spot. I hear userland libs like mapstructure and fastjson can maybe help here.
Two.
Sometimes JSON is all like…
{
"things": {[
"thing: {
}
]}
}
Code language: JSON / JSON with Comments (json)
And sometimes JSON is all like:
[{
"thing": {
}
}]
Code language: JSON / JSON with Comments (json)
I was somehow under the wrong impression that the first example was somehow better. It might be in some cases, like where you might use like things_v2
as an opportunity to “version” the JSON, but generally, I actually think the second example is cleaner.
The second is also easier to deal with in Go, as you don’t need an additional “parent” type to deal with “things”. You can just make the main type a []slice
and it knows what it’s looking for will be an array in the JSON then.
type testURL struct {
Title string `json:"title"`
Value string `json:"value"`
}
exampleJSON := []byte(`[
{"title": "Homepage", "value": "https://nextjs.org/"},
{"title": "GitHub", "value": "https://github.com/vercel/next.js/"},
{"title": "Docs", "value": "https://nextjs.org/docs"}
]`)
var allURLs []testURL
err := json.Unmarshal(exampleJSON, &allURLs)
if err != nil {
fmt.Println(err)
}
Code language: Go (go)
Leave a Reply