Yii2中需创建以Validator结尾的独立验证器类(如PhoneValidator),重写validateAttribute()实现手机号号段等复杂校验;模型rules()中须用完整命名空间引用;支持客户端验证需设置enableClientValidation并注册JS或继承内置验证器。

在Yii2中为模型字段添加特殊业务逻辑校验,比如手机号格式+运营商号段双重验证、密码强度需包含大小写字母和数字、或上传文件必须是PDF且小于5MB,不能只靠内置规则实现。
创建独立验证器类
在@app/components目录下新建PhoneValidator.php文件。
继承yiialidatorsValidator基类,重写validateAttribute()方法。
这一步必须做,否则框架无法识别你的验证器——【类名必须以Validator结尾,且文件名与类名严格一致】。
在validateAttribute()里编写核心逻辑:先用正则匹配11位数字,再查号段表确认归属运营商;任一失败就调用$this->addError($model, $attribute, '手机号不合法');。
在模型中使用自定义验证器
打开目标模型文件(如User.php),在rules()方法中添加规则:
['phone', 'app\components\PhoneValidator']。
注意命名空间要完整,appcomponents对应@app/components路径;如果验证器在@common/components,就得写common\components\PhoneValidator。
这一步漏掉命名空间或路径错误,运行时会直接抛出Class not found异常。
支持客户端验证的写法
方法一:启用AJAX验证
在验证器类中设置public $enableClientValidation = true;,并在init()里注册JS资源:
$this->clientValidate = 'function (attribute, value, messages) { if (!/^1[3-9]d{9}$/.test(value)) messages.push("请输入有效手机号"); }';
方法二:完全禁用客户端验证
在模型规则中加'skipOnEmpty' => true, 'enableClientValidation' => false,强制所有校验走服务端。
方法三:复用内置JS验证逻辑
继承yiialidatorsRegularExpressionValidator而非基类,直接获得pattern属性和默认JS行为,只需覆盖validateAttribute()补充号段校验即可。
带参数的动态验证器
第一步:在验证器类中声明公共属性,例如public $minLength = 8;、public $requireNumber = true;。
第二步:在init()方法中调用parent::init();,然后校验参数合法性——【若$minLength小于1,直接抛出InvalidConfigException】。
第三步:在validateAttribute()中读取这些属性参与判断,比如检查密码长度是否达标、是否含数字等。
第四步:模型规则中传入参数:['password', 'app\components\PasswordValidator', 'minLength' => 10, 'requireNumber' => false]。


















