導入
Web API のリクエスト・レスポンスや設定ファイルなど、外部とデータをやり取りするときの共通フォーマットが JSON です。Go の標準ライブラリ encoding/json を使えば、構造体とJSON文字列を簡単に相互変換できます。
説明
Go の値をJSON文字列に変換することを Marshal(マーシャル)、その逆をJSONから値に戻すことを Unmarshal(アンマーシャル) と呼びます。
package main
import (
"encoding/json"
"fmt"
)
type User struct {
Name string `json:"name"`
Age int `json:"age"`
}
func main() {
u := User{Name: "田中", Age: 30}
// 構造体 → JSON文字列
data, err := json.Marshal(u)
if err != nil {
fmt.Println("エラー:", err)
return
}
fmt.Println(string(data)) // {"name":"田中","age":30}
// JSON文字列 → 構造体
input := []byte(`{"name":"鈴木","age":25}`)
var u2 User
if err := json.Unmarshal(input, &u2); err != nil {
fmt.Println("エラー:", err)
return
}
fmt.Println(u2.Name, u2.Age) // 鈴木 25
}
`json:"name"`… フィールドの後ろに付ける構造体タグ。JSON上のキー名を指定します。これが無いと、Name(大文字始まり)のままJSONキーになってしまいます。json.Marshal(u)… 構造体を[]byte(バイト列)のJSONに変換します。string(data)で文字列として表示できます。json.Unmarshal(input, &u2)… JSONのバイト列を構造体に詰め込みます。書き込み先(&u2)をポインタで渡すのがポイントです。値をそのまま渡すと、関数の中でコピーが書き換わるだけで呼び出し元には反映されません。
構造体タグはほかにも指定ができます。
type Product struct {
Name string `json:"name"`
Price int `json:"price,omitempty"` // 0 のときはJSONに出力しない
Memo string `json:"-"` // 常にJSONに含めない
}
Web API を作るとき(次のレッスンで触れる net/http と組み合わせるとき)は、この encoding/json がリクエストボディの読み取り・レスポンスの組み立ての中心になります。
このサイトの学習用シミュレータは encoding/json に対応していないため、コード例で仕組みを確認してください。実際に動かすには、手元の Go 環境か Go Playground を使います。