日時や日付などのフィールドを扱う際にフィールドごとのタイムゾーンの有無によって、日本時間とUTCのずれによって日付や時間がずれる問題が発生する可能性があります。
この記事では、ずれが生じる仕組みやパターンとその対処法について紹介します。
この記事では、ずれが生じる仕組みやパターンとその対処法について紹介します。
日時フィールドとタイムゾーンについて
日時フィールド、作成日時(_createdAt)、最終更新日時(_updatedAt)にはタイムゾーンの概念があり、DB内ではUTC(協定世界時)で格納されています。※
また、抽出条件の条件式やDBトリガの演算式で使用する
一方で日付、月日、時刻など、日時以外のフィールドにはタイムゾーンの概念は存在しません。
※アプリ利用画面上ではユーザ設定で選択されているタイムゾーンに合わせて表示されるため、日本時間とずれて表示されることはありません。
また、抽出条件の条件式やDBトリガの演算式で使用する
NOW()という関数も、UTCで現在日時を取得します。
一方で日付、月日、時刻など、日時以外のフィールドにはタイムゾーンの概念は存在しません。
※アプリ利用画面上ではユーザ設定で選択されているタイムゾーンに合わせて表示されるため、日本時間とずれて表示されることはありません。
どんな問題が起こるのか
タイムゾーンの概念がある値(日時フィールド、作成日時、最終更新日時、NOW())と、タイムゾーンの概念がないフィールドを組み合わせたときに、日付や時間がずれるということが発生します。
例えば、日本時間はUTC時間と比べて9時間進んでいるため、9時間の時差が生じます。
例えば、日本時間はUTC時間と比べて9時間進んでいるため、9時間の時差が生じます。
※タイムゾーンの概念があるもの同士の組み合わせ、タイムゾーンの概念がないフィールド同士の組み合わせは問題ありません。
日時以外のフィールドにタイムゾーンがある値をマッピングした場合
高度な条件設定で日時以外のフィールドとタイムゾーン有りの値を比較した場合
対処方法
関数設定や高度な条件設定で
※日本以外のタイムゾーンに合わせる場合は、UTCとの時差に合わせてプラスマイナスと時間を修正してください。
+ INTERVAL('9 hours')という記述をすることで、UTC時間から日本時間の9時間をプラスし、日付がずれることを回避することができます。
※日本以外のタイムゾーンに合わせる場合は、UTCとの時差に合わせてプラスマイナスと時間を修正してください。
DBトリガのマッピングの記述例
・現在日時の日付だけを格納する
NOW() + INTERVAL('9 hours')
・作成日時の1か月後の日付を格納する
@DB._createdAt + INTERVAL('1 month') + INTERVAL('9 hours')
高度な条件式の記述例
・入金ステータスが1:未入金かつ入金締切日が現在の日付より前のレコードにメールを送る場合
@status = '1' AND @paymentDue < NOW() + INTERVAL('9 hours')