年月日のバリデーションチェックとフォーマットの変換タイミングについて書き留めておきたくなったので、備忘録としてまとめます!
前提
時刻も含めると長くなるので、本記事では年月日を題材にしています。
また、サンプルコードの言語はJavaとJSを使用しています。
要件は案件/仕様によって様々なので、あくまで一例として捉えていただければと思います。
要件
- 画面上ではyyyy/MM/dd形式で入力、表示すること
- DB上ではDate型でデータを保持すること
- 以下のバリデーションチェックを実施すること
①未入力でないこと
②8桁であること
③数字のみであること
④実在する日付であること
⑤start <= endであること
⑥未来日はNGとする
⑦最大期間制限内であること(ここでは過去2年分とする)
日記記録アプリで、過去2年前までの日記が検索できる機能を実装するイメージです!
バリデーションチェックを行うタイミング
<JS(画面側)でチェックする項目>
①未入力でないこと
②8桁であること
③数字のみであること
④実在する日付であること
⑤start <= endであること
JSでは主に正規表現チェックを行います。
目的1:無駄なリクエストをサーバー側に送らない
目的2:UX(ユーザー体験)の向上
<Java(サーバー側)でチェックする項目>
①未入力でないこと
②8桁であること
③数字のみであること
④実在する日付であること
⑤start <= endであること
⑥未来日はNGとする
⑦最大期間制限内であること(ここでは過去2年分とする)
JavaではJSで行ったチェック項目に加え、業務的な入力チェックを行います。
目的1:値の正当性を保証する
目的2:DBに不正な値を登録させない
JSで実装したバリデーションはクライアント側ですり抜けができてしまうため、あくまで補助的な役割で取り入れるようにし、必ずサーバー側で全てのバリデーションチェックを行うことが大事です!
年月日の変換タイミング
【基本の流れ】
1.入力値をJSでチェック
2.Javaにパラメータを送信する
3.入力値をJavaでチェック
■1. JSのバリデーションチェック
→「yyyy/MM/dd」フォーマットの入力値をDate型に変換してからチェックを行う
例えば2026/1/15~2026/10/01と期間を指定して⑤start <= endのチェックを行う場合、Date型に変換することで"2026/1/15"を"2026/01/15"のように0埋めしてくれるので、正しく日付比較ができるようになります。
const [y, m, d] = yyyyMMddSlash.split('/').map(Number);
return new Date(y, m - 1, d);
■2. Javaにパラメータを送信する
→「yyyy/MM/dd」フォーマットの入力値を「yyyyMMdd」フォーマットに変換する
例えば入力値"2026/1/15"をJava側にDate型で送ってしまうと、"2026-01-12T10:23:00.000Z"のように不要なタイムゾーンが混じってしまったり、日付ズレの事故が起きる可能性があります。
「yyyyMMdd」のフォーマットで送ることで、タイムゾーンの影響を受けず、かつJavaのDateTimeFormatter.BASIC_ISO_DATEでパースすることができるようになります。
DateTimeFormatter.BASIC_ISO_DATEは、「yyyyMMdd」の値をLocalDateに変換するための標準フォーマッタです。
const [y, m, d] = yyyyMMddSlash.split('/');
return y + m.padStart(2, '0') + d.padStart(2, '0');
■3. 入力値をJavaでチェック
→チェック項目①~③は「yyyyMMdd」フォーマットの入力値をString型のままで、
チェック項目④~⑦はLocalDate型に変換してからチェックを行う
以下の基準に沿って型を使い分けるのが望ましいです。
・フォーマットが正しいかを判定する場合→String型でチェックする
・日付として正しいかを判定する場合→LocalDate型でチェックする
LocalDate date = LocalDate.parse("20260112", DateTimeFormatter.BASIC_ISO_DATE);
応用メモ
DBで年月日をDate型にしている場合は、Date型がLocalDate型と『年・月・日を持つ』点で一致するため、上記のバリデーションチェックを終えた後にそのまま値を渡してデータの取得や更新ができます![]()
repository.findByTargetDate(date);