
Cakephp4標準の date() バリデートは2999年までしか対応してないようです。なので、例えば 3000-01-01 などのような日付が渡ってくる場合、問答無用で検証エラーとなります。あまりないケースかもですが、もし 2999年 移行の日付フォーマットチェックをしたい場合、以下のようにするのが良いかと思います。
Cake4: 対応策としてカスタムバリデートで別途日付チェック定義をする
- CustomValidation.php
<?php
declare(strict_types=1);
namespace App\Model\Validation;
use Cake\Validation\Validation;
class CustomValidation extends Validation
{
/**
* 日付フォーマット検証
*
* @param string $data 当該カラム値
* @param array $context コンテキスト リクエストデータ群など
* @return bool
*/
public static function validateDate($data, $context): bool
{
if (preg_match("/^[0-9]{4}-(0[1-9]|1[0-2])-(0[1-9]|[1-2][0-9]|3[0-1])$/", $data)) {
[$y, $m, $d] = explode('-', $data);
if (checkdate((int)$m, (int)$d, (int)$y)) {
return true;
}
}
return false;
}
}
シンプルに preg_match() 関数で日付フォーマット(ここでは yyyy-mm-dd という形)を判定し、それを explode() で抽出しつつ、checkdate() で日付が正しいかを判定して、真偽を返すようにしています。ちなみに、カスタムバリデートメソッドはルールとして public static なメソッドとして定義する必要があります。
あとは、defaultValidation() などで呼び出す形です。
Cake4: 任意のモデルテーブルのバリデートで呼び出す
// 任意のモデルテーブル内で
/**
* デフォルトバリデーション
*
* @param \Cake\Validation\Validator $validator A Validator instance
* @return \Cake\Validation\Validator
*/
public function validationDefault(Validator $validator): Validator
{
$validator->setProvider('customValidation', 'App\Model\Validation\CustomValidation');
$validator
->notEmptyString('start', '開始日を入力してください')
->add('start', 'date', [
'rule' => 'validateDate',
'provider' => 'customValidation',
'message' => '開始日を正しく入力してください',
])
}
setProvider() でカスタムバリデーション定義を読み込んで、$validator->add() 内の provider プロパティで setProvider でセットした名前を呼び出せば、rule でカスタムバリデートメソッドを呼び出すことが可能になります。
■ Cakephp4本体: 標準の date() は2999年まで
https://github.com/cakephp/cakephp/blob/7d9b6a639e5c1f52a813696f6b347726a74f9680/src/Validation/Validation.php#L512-L514