使用 AdditionalFields 与不同 class 中的字段进行比较

Use AdditionalFields to compare to field in a different class

简介

在 MVC Core 中,我有一个基本 ViewModel 和两个 ViewModel 作为属性包含在基本模型中,如下所示:

public class BaseViewModel
{
    public FirstViewModel First { get; set; }    
    public SecondViewModel Second { get; set; }
}

FirstViewModel 中,我在其中一个属性上添加了自定义验证属性,继承自 RemoteAttribute。我的目标是使用此属性将值与 SecondViewModel 中的 属性 进行比较。我已经使用 RemoteAttribute.

AdditionalFields 属性 进行了设置

我认为我的问题在于将 HTML 属性添加到 razor 视图中的控件的方式:

data-val-remote-additionalfields="*.PropOfModelFirst,*.PropOfModelSecond"

当客户端验证调用控制器操作时,*. 被框架替换为 First.,这是错误的,因为第二个值不是 First-class.

的一部分

我尝试将 class 名称添加到第二个 属性 前面,结果是

data-val-remote-additionalfields="*.PropOfModelFirst,*.Second.PropOfModelSecond"

但正如所料,这已更改为 First.Second.PropOfModelSecond。

问题

可以使用 AdditionalFields 属性 与来自另一个 ViewModel 的值进行比较吗?

您不能使用 AdditionalFields 与另一个 ViewModel 的值进行比较。原因是规则是由 jquery.validate.unobtrusive.js 插件添加到 jquery.validate.js(它读取 HtmlHelper 方法生成的 data-val-* 属性)。具体来说,它是 adapters.add("remote", ["url", "type", "additionalfields"], function (options) { 方法,它在 First 之前挂起 属性 名称。

一种选择是使用包含所有属性的单个 'flat' 视图模型。

如果这不是您想要的,那么您可以编写自己的 ajax 代码来调用执行验证的服务器方法。这实际上也有一些额外的性能优势。默认情况下,在 .blur() 事件触发的初始验证后,将对每个 .keyup() 事件执行验证,这意味着如果用户最初输入,您可能会进行大量 ajax 和数据库调用无效值。

删除 [Remote] 属性,并添加以下脚本(我假设属性为 First.ABCSecond.XYZ

$('#First_ABC').change(function() {
    var url = '@Url.Action(...)'; // add your action name
    var input = $(this);
    var message = $('[data-valmsg-for="First.ABC"]'); // or give the element and id attribute
    $.post(url, { abc: input.val(), xyz: $('#Second_XYZ').val() }, function(response) {
        var isValid = response === true || response === "true";
        if (isValid) {
            input.addClass('valid').removeClass('input-validation-error');
            message.empty().addClass('field-validation-valid').removeClass('field-validation-error');
        } else {
            input.addClass('input-validation-error').removeClass('valid');
            message.text(response).addClass('field-validation-error').removeClass('field-validation-valid');
        }
    })
});

控制器方法所在的位置

[HttpPost]
public ActionResult Validate(string abc, string xyz)
{
    bool isValid = .... // code to validate
    if (isValid)
    {
        return Json(true, JsonRequestBehaviour.AllowGet);
    }
    else
    {
        return Json("your error message", JsonRequestBehaviour.AllowGet)
    }
}