経緯
railsでフォームを実装する際にtime_field
を使って営業時間を登録しようとしたがバリデーションがうまくいかず苦戦したため、記録として残しておく。
解決方法
自分がハマった順序を残しておくため3段回に分けて記述をしていく。
1.オプションなしで時間選択ボックスを生成する
<div class="time-field">
<%= f.time_select :open_time %> 〜
<%= f.time_select :close_time %>
</div>
現在の時刻がそのまま表示されるため、設定を忘れていたとしてもバリデーションは通過してしまう。
2. オプションとしてprompt: true
を加える
<div class="time-field">
<%= f.time_select :open_time, prompt: true %> 〜
<%= f.time_select :close_time, prompt: true %>
</div>
これで時刻を選択をしていなければバリデーションで弾かれてエラーが表示されるはず!と思ったが、エラー表示はされない。
3. ignore_date: true
を加える
時間を指定していないはずなのにバリデーションでなぜ弾かれないのかというと年月日の情報も送られているためである。createアクションを実行した時のパラメーターを確認すると以下のようになっている
"open_time(1i)"=>"1", "open_time(2i)"=>"1", "open_time(3i)"=>"1", "open_time(4i)"=>"", "open_time(5i)"=>""
前半の"open_time(1i)"=>"1", "open_time(2i)"=>"1", "open_time(3i)"=>"1"
が年、月、日のデータで、入力していない場合は"1"という値が入って送られてしまうため、バリデーションは通過できてしまう
この事態を回避するためにignore_date
オプションをつける
ignore_date: true
とすることで未入力の場合は送信されず、時刻のみで判定をしてくれる。
"open_time(4i)"=>"", "open_time(5i)"=>"", "close_time(4i)"=>"", "close_time(5i)"=>""
年月日の部分はパラメータに含まれずに無事エラーメッセージを表示することができた。