Laravel8でタイムゾーンが切り替わらない?
Laravel8で日時を扱っていた際、9時間時刻がズレる現象に陥った。
もちろん、config/app.php
の「timezone」は「Asia/Tokyo」に変更済み。
よくよく調べていくと、モデルからそのまま取り出した際は問題ないが、toJson()
をした場合のみ、9時間ズレることに気がついた。
Laravel7から、Date Serializationの仕様が変わったっぽい
これにより、Dateフォーマットが変更になっているだけでなく、
タイムゾーンが強制的にUTCになってしまうとのこと。
https://laravel.com/docs/7.x/upgrade#date-serialization
「Y-m-d H:i:s」フォーマットに変更する
ModelのserializeDate()
をオーバーライドしろと書いてあるので、
Modelを継承した、BaseModelを作ろうと思ったのだが、Userモデルが厄介そうだった。
そのため、トレイトを使用した方法に切り替える。
<?php
namespace App\Models;
use DateTimeInterface;
trait SerializeDate
{
/**
* Prepare a date for array / JSON serialization.
*
* @param \DateTimeInterface $date
* @return string
*/
protected function serializeDate(DateTimeInterface $date)
{
return $date->format('Y-m-d H:i:s');
}
}
上記のファイルを新規で作成し、
各モデルに以下のようにSerializeDate
を追加する。
<?php
namespace App\Models;
use Illuminate\Contracts\Auth\MustVerifyEmail;
use Illuminate\Database\Eloquent\Factories\HasFactory;
use Illuminate\Foundation\Auth\User as Authenticatable;
use Illuminate\Notifications\Notifiable;
class User extends Authenticatable
{
use HasFactory,
Notifiable,
+ SerializeDate;
protected $fillable = [
'name',
'email',
'password',
];
protected $hidden = [
'password',
'remember_token',
];
protected $casts = [
'email_verified_at' => 'datetime',
];
}
これによって、日時フォーマットが「Y-m-d H:i:s」となり、
当初の目的であった時刻の9時間ズレも解決した。