Yii. Еще немного о валидации
Не так давно столкнулась с необходимостью генерации правил валидации "на лету", то есть динамически. В обычном случае вся валидация осуществлялась на основе заранее описанных правил в rules() и собственно дополнительных условий в beforeValidate().
А что, если у нас нет заранее описанной модели? В таком случае мы можем воспользоваться методами CValidator!
Если открыть сам класс, то можно увидеть много интересного.
Например, тут мы видим список предустановленных валидаторов в виде массива (имя валидатора => класс).
Таким образом, в любом месте мы можем динамически создавать правила валидации, даже если таковые не были описаны должным образом в нужной нам модели.
Первый пример, который приходит на ум, где использование данного метода наиболее уместно - сделать атрибут обязательным при выполнении определенного условия. Например, если выбран метод доставки (type_delivery) "Курьером", то сделать поле "Желаемое время доставки" (time_delivery) обязательным. Для этого в beforeValidate() просто добавляем условие:
В этом примере мы видим использование метода модели getValidatorList(), который возвращает все определенные в модели валидаторы. Метод возвращает объект класса CList, поэтому вы можете манипулировать им, вставляя и удаляя валидаторы.
Еще один полезный метод класса CModel - getValidators($attribute=null) - возвращает валидаторы, применимые к текущему сценарию. В качестве параметра может быть передано имя атрибута, валидаторы которого должны быть получены. Если параметр не передан, будут получены валидаторы ВСЕХ атрибутов модели.
Используя эти методы, можно расширить встроенные возможности Yii и изменить их под свои нужды.
А что, если у нас нет заранее описанной модели? В таком случае мы можем воспользоваться методами CValidator!
Если открыть сам класс, то можно увидеть много интересного.
Например, тут мы видим список предустановленных валидаторов в виде массива (имя валидатора => класс).
public static $builtInValidators=array(
'required'=>'CRequiredValidator',
'filter'=>'CFilterValidator',
'match'=>'CRegularExpressionValidator',
'email'=>'CEmailValidator',
'url'=>'CUrlValidator',
'unique'=>'CUniqueValidator',
'compare'=>'CCompareValidator',
'length'=>'CStringValidator',
'in'=>'CRangeValidator',
'numerical'=>'CNumberValidator',
'captcha'=>'CCaptchaValidator',
'type'=>'CTypeValidator',
'file'=>'CFileValidator',
'default'=>'CDefaultValueValidator',
'exist'=>'CExistValidator',
'boolean'=>'CBooleanValidator',
'safe'=>'CSafeValidator',
'unsafe'=>'CUnsafeValidator',
'date'=>'CDateValidator',
);
Но больше всего нас интересует метод createValidator($name,$object,$attributes,$params=array()). Параметры метода:- name - имя или класс валидатора. Здесь необходимо указать имя из того самого списка предустановленных валидаторов или же имя класса предустановленного или собственного валидатора.
- object - валидируемый объект данных CModel.
- attributes - список валидируемых атрибутов. Может быть либо массивом имен атрибутов, либо строкой имен атрибутов, разделенных запятой.
- params - дополнительные параметры. Например, параметр 'on' - для каких сценариев будет использоваться валидатор, или 'message' - сообщение об ошибке.
Таким образом, в любом месте мы можем динамически создавать правила валидации, даже если таковые не были описаны должным образом в нужной нам модели.
Первый пример, который приходит на ум, где использование данного метода наиболее уместно - сделать атрибут обязательным при выполнении определенного условия. Например, если выбран метод доставки (type_delivery) "Курьером", то сделать поле "Желаемое время доставки" (time_delivery) обязательным. Для этого в beforeValidate() просто добавляем условие:
if ($this->type_delivery == 2) {
$this->getValidatorList()->add(CValidator::createValidator('required', $this, 'time_delivery'));
}
Пример банальный, но думаю, суть ясна :)В этом примере мы видим использование метода модели getValidatorList(), который возвращает все определенные в модели валидаторы. Метод возвращает объект класса CList, поэтому вы можете манипулировать им, вставляя и удаляя валидаторы.
Еще один полезный метод класса CModel - getValidators($attribute=null) - возвращает валидаторы, применимые к текущему сценарию. В качестве параметра может быть передано имя атрибута, валидаторы которого должны быть получены. Если параметр не передан, будут получены валидаторы ВСЕХ атрибутов модели.
Используя эти методы, можно расширить встроенные возможности Yii и изменить их под свои нужды.
prikolno
ОтветитьУдалить