はじめに
今回は、JavaScriptとSQLの日付解釈の違いについて、
ありがちな例を用いて解説してみようと思います。
例えば以下のような2パターンのコードがあるとします。
※Node.jsのTypeORMを使用しています。
Aのコード
const hogeDate = "2023-07-30"
const date = new Date(hogeDate);
builder.andWhere('projects.hogeDate <= :hogeDate', { hogeDate: date });
Bのコード
builder.andWhere("projects.hogeDate <= DATE '2023-07-30'");
これらのコードは一見同じ結果になるように見えます。
何が問題なのか
まずAのコードですが、hogeDate
はJavaScriptのDateオブジェクト
として作成されています。
JavaScriptのDateオブジェクトは、デフォルトでは実行環境のタイムゾーンに基づいて解釈されるため、dateの値は文字列hogeDate("2023-07-30")
が自身のタイムゾーンに基づいて解釈された日付と時間になります。
それに対してBのコードでは、DATE
を使ってSQLの日付リテラル
を直接使用しています。
このためSQLサーバの設定により、タイムゾーンが異なる可能性があります。
SQLでは日付リテラルは通常であれば、UTCで解釈されるので、
"2023-07-30"
はUTCでの"2023-07-30 00:00:00"
を指すことになるということです。
まとめ
日付解釈問題は比較的あるあるかと思いますが、
使用しているデータベースとその日付や時間の解釈方法、および実行環境のタイムゾーン設定を考慮に入れて、日付/時間の比較を行うことが大事ということですね。
おしまい。