#validation #asp.net-mvc-3 #data-annotations
#проверка #asp.net-mvc-3 #данные-аннотации
Вопрос:
У меня есть простая форма, которая использует ASP.NET MVC 3 ненавязчивая проверка на стороне клиента.
Модель выглядит примерно так (имена изменены в целях конфиденциальности):
public class MyInputModel
{
public MyInputModel()
{
}
public MyInputModel(MyViewData viewData)
{
ViewData = viewData;
MaxValueForSize = viewData.MaxSize;
}
public int MaxValueForSize { get; set; }
[RegularExpression("[1-9][0-9]*",ErrorMessage = "The value must be a whole number.")]
public int Size { get; set; }
[StringLength(255)]
[Required]
public string Description{ get; set; }
}
На мой взгляд, я ввел скрытое поле в для MaxValueForSize
и я хочу сравнить введенное значение для Size
с меньшим или равным MaxValueForSize
свойству.
Я знаю, что могу сделать это на стороне сервера, переопределив атрибут проверки следующим образом:
internal class SizeValidAttribute : ValidationAttribute
{
protected override ValidationResult IsValid(object value, ValidationContext validationContext)
{
if(value != null)
{
var model = (MyInputModel) validationContext.ObjectInstance;
if ((int)value > model.MaxValueForSize)
return new ValidationResult(ErrorMessage);
}
return base.IsValid(value, validationContext);
}
}
Однако я хотел бы (необходимо) провести проверку этого свойства на стороне клиента. Аналогично тому, как работает Compare
аннотация.
Кто-нибудь знает способ сделать это? Нужно ли мне как-то расширить проверку на стороне клиента?
Спасибо за вашу помощь.
Ответ №1:
Взгляните на эту статью. В нем объясняется, как расширить ASP.NET Проверка модели MVC для поддержки проверки в разных полях:
Расширение ASP.NET Проверка MVC
http://blogs.msdn.com/b/mikeormond/archive/2010/10/05/extending-asp-net-mvc-s-validation.aspx
Комментарии:
1. Это решение было действительно полезным. Я попробовал это в MVC2, и это сработало, но мне пришлось расположить свойства модели в правильном порядке. Похоже, что установка значения свойства и запуск проверки этого свойства выполняются в одном цикле. Если вы хотите получить доступ к другому свойству в модели, то оно должно быть первым (по номеру строки), чтобы оно было установлено первым. Так что будьте осторожны, это ловушка!
Ответ №2:
Ответ Роберта Харви указал мне правильный путь, но это возможно с ASP.NET MVC3, чтобы довольно просто переопределить проверку, используя следующий шаблон:
public class LessThanOrEqualToPropertyAttribute : ValidationAttribute, IClientValidatable
{
public string OtherProperty { get; set; }
public override bool IsValid(object value)
{
return true;
}
protected override ValidationResult IsValid(object value, ValidationContext validationContext)
{
if (value != null)
{
PropertyInfo propertyInfo = validationContext.ObjectType.GetProperty(OtherProperty);
var otherValue = propertyInfo.GetGetMethod().Invoke(validationContext.ObjectInstance, null);
if ((int)otherValue < (int)value)
return new ValidationResult(ErrorMessage);
}
return base.IsValid(value, validationContext);
}
public IEnumerable<ModelClientValidationRule> GetClientValidationRules(ModelMetadata metadata, ControllerContext context)
{
var rule = new ModelClientValidationRule
{
ValidationType = "lessthanorequaltoproperty",
ErrorMessage = FormatErrorMessage(ErrorMessage),
};
rule.ValidationParameters.Add("otherproperty", OtherProperty);
yield return rule;
}
}
Это было не совсем ясно из различной конфликтующей документации, которую я нашел.
Ответ №3:
Я знаю, что это поздно, но, чтобы вернуться к превосходному самоответу RSL, единственное, чего действительно не хватало, это клиентского скрипта для добавления ненавязчивого адаптера проверки. Хороший пример такого здесь.