$.validator.unobtrusive.adapters.addBool() 不起作用
$.validator.unobtrusive.adapters.addBool() does not work
在 asp.net 核心 Razor Pages 应用程序中,使用 jquery 不显眼的验证,我试图让自定义验证属性在客户端工作。表单由 bootstrap 模态弹出窗口中的 fetch() 调用呈现,这可能与问题有关,尽管我在框架 4.8 asp.net mvc 中遇到完全相同的问题通过 ajax 调用呈现表单的应用程序。
在 Razor Pages 应用程序中,我以通常的方式设置了服务器端属性:
public class TerminationReasonCodeAttribute : ValidationAttribute, IClientModelValidator
{
private const string errorMessage = "When a Termination Reason is selected, a Termination Date must be entered, and vice-versa.";
public void AddValidation(ClientModelValidationContext context)
{
MergeAttribute(context.Attributes, "data-val", "true");
MergeAttribute(context.Attributes, "data-val-terminationreasoncode", errorMessage);
}
private bool MergeAttribute(
IDictionary<string, string> attributes,
string key,
string value)
{
if (attributes.ContainsKey(key))
{
return false;
}
attributes.Add(key, value);
return true;
}
...rest of code omitted for brevity.
属性被添加到class的属性中,以通常的方式呈现在表单中:
[TerminationReasonCode]
[StringLength(50)]
[Display(Name = "Termination Reason")]
public string TerminationReasonCode { get; set; }
有问题的表单是通过对服务器端方法的 fetch() 调用并设置 div 的 innerHTML 呈现的,如下所示:
div.querySelector('div.modal-body').innerHTML = cleanHtml;
因为我要异步呈现表单,所以我必须重新解析它:
let $form = $(div).find('#editUserForm');
$form.removeData('validator').removeData('unobtrusiveValidation');
$.validator.unobtrusive.parse($form);
然后我调用 addMethod:
$.validator.addMethod("terminationreasoncode",
function (value, element, param) {
//the attribute is applied to TerminationReasonCode. this is arbitrary
//it could have been applied to TerminationDate
let terminationReason = value;
let terminationDate = document.getElementById('TerminationDate').value;
if (terminationReason && !terminationDate) {
return false;
}
else if (terminationDate && !terminationReason) {
return false;
}
else {
return true;
}
});
最后,我称之为:
$.validator.unobtrusive.adapters.addBool("terminationreasoncode");
在我的表单中,当用户单击“保存”按钮时,我调用 $("#editUserForm").valid()。我的自定义验证方法从未触发,我也不知道为什么。当我查看呈现的内容时,我可以看到我所有的“数据-...”标签都得到了正确呈现:
<select name="TerminationReasonCode" id="TerminationReasonCode"
data-val-terminationreasoncode="When a Termination Reason is selected, a Termination Date must be
entered, and vice-versa."
data-val-length-max="50"
data-val-length="The field Termination Reason must be a string with a maximum length of 50."
data-val="true"
class="form-control">
关键在于:如果我没有调用 $.validator.unobtrusive.adapters.addBool("terminationreasoncode"),而是执行您在下面看到的代码,它就可以工作!当我在 javascript 中调用 $("#editUserForm").valid() 时,我的验证方法被调用。为什么下面的代码可以工作,但对 addBool 的调用什么都不做?同样,我在 asp.net mvc Framework 4.8 应用程序中遇到完全相同的问题,其中表单由 ajax 调用呈现,并且相同的解决方法在那里工作。
$('#TerminationReasonCode').rules('add',
{
terminationreasoncode: true,
messages: { terminationreasoncode: "When a Termination Reason is selected, a Termination Date must be entered, and vice-versa." }
});
答案是这个调用:
$.validator.unobtrusive.parse($form);
必须在此调用之后发生:
$.validator.unobtrusive.adapters.addBool("terminationreasoncode");
其他一切正常,即使它在 parse() 之后运行,除了调用 addBool()。对 addBool() 的调用必须在对 parse() 的调用 之前 执行。如果有人知道为什么会这样,请post回答,我会select。
在 asp.net 核心 Razor Pages 应用程序中,使用 jquery 不显眼的验证,我试图让自定义验证属性在客户端工作。表单由 bootstrap 模态弹出窗口中的 fetch() 调用呈现,这可能与问题有关,尽管我在框架 4.8 asp.net mvc 中遇到完全相同的问题通过 ajax 调用呈现表单的应用程序。
在 Razor Pages 应用程序中,我以通常的方式设置了服务器端属性:
public class TerminationReasonCodeAttribute : ValidationAttribute, IClientModelValidator
{
private const string errorMessage = "When a Termination Reason is selected, a Termination Date must be entered, and vice-versa.";
public void AddValidation(ClientModelValidationContext context)
{
MergeAttribute(context.Attributes, "data-val", "true");
MergeAttribute(context.Attributes, "data-val-terminationreasoncode", errorMessage);
}
private bool MergeAttribute(
IDictionary<string, string> attributes,
string key,
string value)
{
if (attributes.ContainsKey(key))
{
return false;
}
attributes.Add(key, value);
return true;
}
...rest of code omitted for brevity.
属性被添加到class的属性中,以通常的方式呈现在表单中:
[TerminationReasonCode]
[StringLength(50)]
[Display(Name = "Termination Reason")]
public string TerminationReasonCode { get; set; }
有问题的表单是通过对服务器端方法的 fetch() 调用并设置 div 的 innerHTML 呈现的,如下所示:
div.querySelector('div.modal-body').innerHTML = cleanHtml;
因为我要异步呈现表单,所以我必须重新解析它:
let $form = $(div).find('#editUserForm');
$form.removeData('validator').removeData('unobtrusiveValidation');
$.validator.unobtrusive.parse($form);
然后我调用 addMethod:
$.validator.addMethod("terminationreasoncode",
function (value, element, param) {
//the attribute is applied to TerminationReasonCode. this is arbitrary
//it could have been applied to TerminationDate
let terminationReason = value;
let terminationDate = document.getElementById('TerminationDate').value;
if (terminationReason && !terminationDate) {
return false;
}
else if (terminationDate && !terminationReason) {
return false;
}
else {
return true;
}
});
最后,我称之为:
$.validator.unobtrusive.adapters.addBool("terminationreasoncode");
在我的表单中,当用户单击“保存”按钮时,我调用 $("#editUserForm").valid()。我的自定义验证方法从未触发,我也不知道为什么。当我查看呈现的内容时,我可以看到我所有的“数据-...”标签都得到了正确呈现:
<select name="TerminationReasonCode" id="TerminationReasonCode"
data-val-terminationreasoncode="When a Termination Reason is selected, a Termination Date must be
entered, and vice-versa."
data-val-length-max="50"
data-val-length="The field Termination Reason must be a string with a maximum length of 50."
data-val="true"
class="form-control">
关键在于:如果我没有调用 $.validator.unobtrusive.adapters.addBool("terminationreasoncode"),而是执行您在下面看到的代码,它就可以工作!当我在 javascript 中调用 $("#editUserForm").valid() 时,我的验证方法被调用。为什么下面的代码可以工作,但对 addBool 的调用什么都不做?同样,我在 asp.net mvc Framework 4.8 应用程序中遇到完全相同的问题,其中表单由 ajax 调用呈现,并且相同的解决方法在那里工作。
$('#TerminationReasonCode').rules('add',
{
terminationreasoncode: true,
messages: { terminationreasoncode: "When a Termination Reason is selected, a Termination Date must be entered, and vice-versa." }
});
答案是这个调用:
$.validator.unobtrusive.parse($form);
必须在此调用之后发生:
$.validator.unobtrusive.adapters.addBool("terminationreasoncode");
其他一切正常,即使它在 parse() 之后运行,除了调用 addBool()。对 addBool() 的调用必须在对 parse() 的调用 之前 执行。如果有人知道为什么会这样,请post回答,我会select。