Yii2 自定义验证器不按照指南建议工作

Yii2 custom validator not working as guide suggests

我今天在这里搜索了一段时间,但我不明白为什么我的验证器不能在我的模型中工作。

我在下面的代码中有一个带有模型 "Page" 的模块。

我需要使用 2 个属性来验证模型。他们是 hero_link 和 hero_linked。如果 hero_linked 为真,我想要求 hero_link.

在指南 here 中,他们解释了这种验证器的正确语法

我在我的模型中使用了这种语法,但它没有像我预期的那样有效。我也添加了 whenClient 属性,所以我可以在这里使用客户端验证。

我的相关代码如下:

// Page model
namespace common\modules\page\models;

use Yii;

class Page extends \yii\db\ActiveRecord
{
    public function rules()
    {
        return [
            [['hero_linked',], 'boolean'],
            [['hero_linked',], 'required'],
            [['hero_link',], 'string', 'max' => 255],
            [
                'hero_link', 
                'required', 
                'when' => function($model) {
                    return $model->hero_linked == true;
                },
                'whenClient' => "function (attribute, value) {
                    return $('#page-hero_linked').val() == '1';
                }",
            ],
        ];
    }
}

// _form view 
<?php $form = ActiveForm::begin(); ?>
    <?= $form->field($model, 'hero_linked')->checkbox() ?>
    <?= $form->field($model, 'hero_link')->textInput(['maxlength' => 255]) ?>
<?php ActiveForm::end(); ?>

所需的验证器已正确应用,但它似乎忽略了 属性 时的要求,即使我的复选框未选中也是如此。我的语法不正确,还是我缺少要求?感谢您的帮助,在此先感谢!

我找到了如何进行这项工作。如果您使用复选框,则不能仅使用服务器端或客户端验证。我不得不同时使用 when 和 whenClient。我必须在我的视图中注册一个脚本,以便选中的属性会在复选框上更新。

$('label > #page-hero_linked').click(function(event) {
    var checked = $(this).attr('checked');
    if (checked) {
        $(this).removeAttr('checked');
    }else{
        $(this).attr('checked', '');
    };
});

以下是我的验证规则。

[['hero_link'],
'required',
'when' => function($model) {
    return $model->hero_linked == true;
},
'whenClient' => "function (attribute, value) {
    return $('#page-hero_linked').attr('checked');
}",],

总而言之,使它工作的代码非常简单,但对我来说并不清楚文档需要这么多。

我猜这就是你想要的。 首先在输入框的whenClient中使用属性 "checked"来获取复选框是否被选中。

复选框的隐藏字段不是问题。

hero_linked(复选框)中的 whenClient 用于在更改复选框时验证 hero_link(文本输入)字段。 因此,您可以立即查看是否需要 hero_link(文本输入)。

如果您使用此规则,您的表单中不需要任何额外的 js 代码。

但正如您可能还看到的那样,由于完整的名称 "page-something" 这实际上只针对 "page" 模型,我想也取决于表单名称。所以你应该为 form.php 中的两个字段使用一些其他固定的 "id's" 所以如果你将你的页面模型扩展到另一个 class.

[
    'hero_linked', 'required',
    'whenClient' => "function (attribute, value) {
        $('form').yiiActiveForm('validateAttribute', 'page-hero_link');
        return true;
    }",
],
[['hero_link',], 'string', 'max' => 255],
[
    'hero_link', 'required', 'when' => function ($model) {
        return $model->hero_linked == true;
    },
    'whenClient' => "function (attribute, value) {
        return $('#page-hero_linked').prop('checked');
    }",
],