Sometimes you need to validate values that are not bound to any model. You can use the yii\base\DynamicModel class, which supports defining both attributes and rules on the fly.
Step 1 − Add the actionAdHocValidation method to the SiteController.
public function actionAdHocValidation() { $model = DynamicModel::validateData([ 'username' => 'John', 'email' => 'john@gmail.com' ], [ [['username', 'email'], 'string', 'max' => 12], ['email', 'email'], ]); if ($model->hasErrors()) { var_dump($model->errors); } else { echo "success"; } }
In the above code, we define a “dynamic” model with username and email attributes and validate them.
Step 2 − Type http://localhost:8080/index.php?r=site/ad-hoc-validation in the address bar of the web browser, you will see an error message because our email is 14 characters long.
There are two types of custom validators −
An inline validator is defined by a model method or an anonymous function. If an attribute fails the validation, you should call the yii\base\Model::addError() method to save the error message.
The following example of the RegistrationForm validates the city property, so it can accept only two values – London and Paris.
<?php namespace app\models; use Yii; use yii\base\Model; class RegistrationForm extends Model { public $username; public $password; public $email; public $country; public $city; public $phone; public function rules() { return [ ['city', 'validateCity'] ]; } public function validateCity($attribute, $params) { if (!in_array($this->$attribute, ['Paris', 'London'])) { $this->addError($attribute, 'The city must be either "London" or "Paris".'); } } } ?>
A standalone validator extends the yii\validators\Validator class. To implement the validation logic, you should override the yii\validators\Validator::validateAttribute() method.
Step 1 − To implement the previous example using the standalone validator, add a CityValidator.php file to the components folder.
<?php namespace app\components; use yii\validators\Validator; class CityValidator extends Validator { public function validateAttribute($model, $attribute) { if (!in_array($model->$attribute, ['Paris', 'London'])) { $this->addError($model, $attribute, 'The city must be either "Paris" or "London".'); } } } ?>
Step 2 − Then, modify the RegistrationForm model this way.
<?php namespace app\models; use app\components\CityValidator; use Yii; use yii\base\Model; class RegistrationForm extends Model { public $username; public $password; public $email; public $country; public $city; public $phone; public function rules() { return [ ['city', CityValidator::className()] ]; } } ?>