У меня есть следующий настраиваемый атрибут requiredif и добавлен сценарий на стороне клиента, а проверка на стороне сервера работает. тег обновляется атрибутами data-val, но проверка на стороне клиента не запускается. Не могу понять, что мне здесь не хватает
public class RequiredIfAttribute : ValidationAttribute, IClientModelValidator//ValidationAttribute
{
private string dependentProperty;
private object targetValue;
public RequiredIfAttribute(string _DependentProperty, object _TargetValue)
{
this.dependentProperty=_DependentProperty ;
this.targetValue=_TargetValue ;
}
public void AddValidation(ClientModelValidationContext context)
{
MergeAttribute(context.Attributes, "data-val-requiredif-dependentproperty", dependentProperty);
MergeAttribute(context.Attributes, "data-val-requiredif-targetvalue","true");
MergeAttribute(context.Attributes, "data-val-requiredif",GetErrorMessage(context));
}
bool MergeAttribute(IDictionary<string, string> attributes, string key, string value)
{
if (attributes.ContainsKey(key))
{
return false;
}
attributes.Add(key, value);
return true;
}
private string GetErrorMessage(ClientModelValidationContext context)
{
return string.Format("{0} is not a valid",
context.ModelMetadata.GetDisplayName());
}
protected override ValidationResult IsValid(object value, System.ComponentModel.DataAnnotations.ValidationContext validationContext)
{
var propertyTestedInfo = validationContext.ObjectType.GetProperty(this.dependentProperty);
if (propertyTestedInfo == null)
{
return new ValidationResult(string.Format("{0} needs to be exist in this object.", this.dependentProperty));
}
var dependendValue = propertyTestedInfo.GetValue(validationContext.ObjectInstance, null);
if (dependendValue == null)
{
return new ValidationResult(string.Format("{0} needs to be populated.", this.dependentProperty));
}
if (!dependendValue.Equals(this.targetValue))
{
var fieldValue = validationContext.ObjectType.GetProperty(validationContext.MemberName).GetValue(validationContext.ObjectInstance, null);
if (fieldValue != null)
{
return ValidationResult.Success;
}
else
{
return new ValidationResult(string.Format("{0} cannot be null", validationContext.MemberName));
}
}
else
{
// Must be ignored
return ValidationResult.Success;
}
}
}
Код Javascript
<script>
$.validator.addMethod('requiredif',
function (value, element, parameters) {
var id = '#' + parameters['dependentproperty'];
// get the target value (as a string,
// as that's what actual value will be)
var targetvalue = parameters['targetvalue'];
targetvalue =
(targetvalue == null ? '' : targetvalue).toString();
// get the actual value of the target control
// note - this probably needs to cater for more
// control types, e.g. radios
var control = $(id);
var controltype = control.attr('type');
var actualvalue =
controltype === 'checkbox' ?
control.attr('checked').toString() :
control.val();
// if the condition is true, reuse the existing
// required field validator functionality
if (targetvalue === actualvalue)
return $.validator.methods.required.call(
this, value, element, parameters);
return true;
}
);
$.validator.unobtrusive.adapters.add(
'requiredif',
['dependentproperty', 'targetvalue'],
function (options) {
options.rules['requiredif'] = {
dependentproperty: options.params['dependentproperty'],
targetvalue: options.params['targetvalue']
};
options.messages['requiredif'] = options.message;
});
</script>
Сгенерированный тег и свойство класса выглядят следующим образом
<select data-val-requiredif="ToPositionID is not a valid" data-val-requiredif-dependentproperty="chkToPosReq" data-val-requiredif-targetvalue="true" id="ToPositionID" name="ToPositionID">
Класс
public class VMWorkflow
{
[RequiredIf("chkToPosReq", "1")]
public int? ToPositionID { get; set; }
}