Rails 7 で追加されたComparisonValidatorで日付のバリデーションを実装する

この記事は GMOアドマーケティング Advent Calendar 2022 3日目の記事です。

はじめに

こんにちは。
GMOアドマーケティングの石丸(@thomi40)です。

前回の記事では Rails 7 から実装された query_log_tags について紹介しました。

はじめにこんにちは。GMOアドマーケティングの石丸(@thomi40)です。以前、本ブログでRails 6.1に新しく追加された機能について紹介しました。今回はRails 7から追加された「query_log_tags」について紹介します。query_log_tagsとは?query_log_tags は Active Record のオプションの一つで、設定を有効にすることでクエリのログに自動でコメントを追加することができる機能です。元々は「Marginalia」というGemで実装されていた機能とのこと。詳細リンクAdd Marginalia to Rails, via QueryLogs by keeran · Pull Request #42240 · ra...

今回の記事では同じく Rails 7 から追加された ComparisonValidator について紹介します。
※記事内の画像は筆者が作成したアプリケーションをキャプチャーしたものです。

ComparisonValidatorとは

ComparisonValidator は任意のオブジェクトの比較を行うバリデーターです。
数値の比較には NumericalityValidator を使うことが一般的ですが、NumericalityValidator は日付の比較には使うことができないため、日付の比較を行う場合は独自のバリデーションの実装や専用のgemを導入する必要がありました。
Rails 7から実装された ComparisonValidator では、数値だけでなく日付に関する比較としても利用することが可能なので、比較用のバリデーターとして非常に便利です。
早速動作を見ていきましょう。

検証用のアプリ作成

ComparisonValidator の動作を確認するために簡易的なアプリケーションを作成します。
今回は Rails: 7.0.4, Ruby: 3.1.2 の環境で構築しました。
日付の比較を行いたいため、以下のコマンドで雛形を作成します。
作成されたmigrationファイルはこちら。
scaffoldで作成されたビューのフォーム(新規作成画面)はこちら。

日付に関するバリデーションを実装

まずは独自でバリデーションを実装してみます。
今回は例として「終了日(end_date)は開始日(start_date)より前の日を設定できないようにする」というバリデーションを実装してみます。
期待通りバリデーションが動作しました。
※動作確認用なので日本語化の対応は行ってません。

続いて ComparisonValidator で同じ条件のバリデーションを実装してみます。
greater_than のオプションで実装したため、先程と同様に終了日(end_date)は開始日(start_date)より大きい値(後の日付)になっているかどうかを検証するバリデーションが表示されました。

独自でバリデーションを実装する必要がないため、シンプルなコードで実装することができますね。

さいごに

今回はRails 7から追加されたComparisonValidatorについて紹介しました。
今回は日付に関するバリデーションを例として紹介しましたが、ComparisonValidatorは文字列や数値の比較としても利用する事が可能です。
greater_than 以外にも値が等しいかどうかを検証する equal_to や 以上 or 以下を検証する greater_than_or_equal_toless_than_or_equal_to などのオプションも用意されています。

オプションの詳細や実装の背景は以下の参考リンクからご確認ください。

参考リンク

告知

明日は天河さんによる「ぼくのかんがえたさいきょうのChromeカスタマイズ」についてです。

引き続き、GMOアドマーケティング Advent Calendar 2022 をお楽しみください!

■学生インターン募集中!
https://note.gmo-ap.jp/n/nc42c8a60afaf

■エンジニア採用ページはこちら!
https://note.gmo-ap.jp/n/n02cbeb6edb0d

■GMOアドパートナーズ 公式noteはこちら!
https://note.gmo-ap.jp/