json型の扱いについてまとまったページがあまりなかったので書くことにしました。
・・・いまだに苦しめられています。
環境
larave5.7
Mysql5.7
##1.データベースにjson型を含むテーブルをmigrationで作成するとき
public function up()
{
Schema::create('members', function (Blueprint $table) {
$table->uuid('id');
$table->string('name', 100);
$table->json('data')->nullable(); // ココ
$table->timestamps();
$table->primary('uuid');
});
}
※注意
なんと、Mysql5.7のJson型は初期値を設定できない仕様になっています・・・!(MariaDBは初期値OK)
$table->json('data')->default('{"title":1,"permission":[1,2]}');
というかんじに書いてたらmigrate実行時にエラーが出ました。
MariaDBで開発してるけどリリース先の環境はMysqlって場合は特に気をつけてください。(もちろんDB揃えられるなら揃えてください!)
##2.データベースにデータを入れるとき
こちらにすでに書かれてましたhttps://qiita.com/kamikosi/items/7d4135ce74de8b91e721
$data = [
[
'title' => 1,
'permission' => [
1,
2,
],
],
[
'title' => 2,
'permission' => [
1,
2,
],
]
];
$member = new Member;
$member->data = $data; // ココ
$member->save();
※注意
$member->data = json_encode($data);
と書くとstringとしてデータが入ってしまう。
↓がそのjson_encodeしてしまったデータ。
"{\"permission_list\":[{\"title\":\"2\",\"permission\":[\"1\",\"3\"]}],\"admin\":false}"
JSON_UNESCAPED_UNICODEオプションを付けても両端の"
はのこってしまうので
json型として取得できなくなってしまう。。。
##3.データベースからデータを取得するとき
参考:https://qiita.com/pinekta/items/93c9c427ccc22df578a5
まず、モデル側に$castsを設定する。
class Member extends Eloquent
{
protected $casts = [
'json_column' => 'json', // ココ
];
}
$castsについてはjson型だけでなく、データをDBから取得するときの型を設定できるものなので
知っておくと応用がききそうです。
つぎにそのモデルを使ってデータを取得します。
$member = Member::find($id);
// $member->dataにはjsonが連想配列として保存されている
$data_permission = isset($member->data['permission']) ? $member->data['permission'] : null ;
$castsによってjson型データが連想配列として取得できるようになっているので
$member->data['permission']
のように取得できる。
json objectとしてデータベースに入れていても、取得すると連想配列になっているのでネスト地獄に注意。。。(絶賛苦戦中)
また1.の注意欄でも書いた通り、初期値設定ができないので
特定のキーが存在するかどうかのチェック(こちらではissetを使用)が必要です。
まだまだlaravel, MysqlのJson型については勉強中の身ですので
「こうすれば{もっとかんたんだよ|できるよ}」などのご意見をいただけましたら幸いです。