Пользовательский DataAnnotations ValueAttribute, поддерживающий различные сообщения об ошибках при проверке на стороне клиента и на стороне сервера

Я создал пользовательскую аннотацию данных, которая работает должным образом на стороне клиента, и корректно отображает пользовательское сообщение, когда введенная дата недействительна. Однако, если запись не проходит проверку на стороне сервера, возвращается сообщение об ошибке по умолчанию. Я не могу добраться до корня того, почему пользовательское сообщение также не отображается при сбое проверки на стороне сервера. Пошагово, все выглядит нормально в отладчике, но вывод в конечном итоге неверен. Любая помощь приветствуется!

public class DobViewModel
{
   [DateTypeWithPhrase()]
   public DateTime? DateOfBirth { get; set; }    
}

public class DataTypeWithPhraseAttributeAdapter : DataAnnotationsModelValidator<DateTypeWithPhraseAttribute>
{
   private readonly DateTypeWithPhraseAttribute _attribute;

   public DataTypeWithPhraseAttributeAdapter(ModelMetadata metadata, ControllerContext context, DateTypeWithPhraseAttribute attribute)
          : base(metadata, context, attribute)
   {
        _attribute = attribute;
   }

    public static void SelfRegister()
    {
         DataAnnotationsModelValidatorProvider
              .RegisterAdapter(
                  typeof(DateTypeWithPhraseAttribute),
                  typeof(DataTypeWithPhraseAttributeAdapter));
    }

    public override IEnumerable<ModelClientValidationRule> GetClientValidationRules()
    {
        return new[] { new ModelClientValidationDateRule(_attribute.ErrorMessage) };
    }
}

public class DateTypeWithPhraseAttribute : DataTypeAttribute
{
    public DateTypeWithPhraseAttribute() : base(DataType.Date)
    {
         ErrorMessageResourceName = null;
         ErrorMessage = ErrorPhrase;
    }

    public string ErrorPhrase = "Invalid Date";
 }

1 ответ

Решение

Кажется, ошибка была вызвана при привязке при обратной передаче. Если дата недействительна, она распознает, что произошла ошибка, и установит значение DateOfBirth в значение null, которое пройдет пользовательскую проверку. Однако, это уже не удалось, следовательно, возвращается сообщение по умолчанию.

Решение, которое я реализовал, состояло в том, чтобы изменить DateOfBirth, чтобы быть строкой, это тогда связало бы правильно. Затем я переопределил метод IsValid, чтобы проверить, действительно ли строка была действительной датой.

public class DobViewModel
{
   [DateTypeWithPhrase()]
   public string DateOfBirth { get; set; }    
}

public class DateTypeWithPhraseAttribute : DataTypeAttribute
{
    public DateTypeWithPhraseAttribute() : base(DataType.Date)
    {
         ErrorMessageResourceName = null;
         ErrorMessage = ErrorPhrase;
    }

    public string ErrorPhrase = "Invalid Date";

    protected override ValidationResult IsValid(object value, ValidationContext validationContext)
    {
        DateTime myDate;
        if (value == null || DateTime.TryParse(value.ToString(), out myDate))
        {
            return ValidationResult.Success;
        }
        return new ValidationResult(ErrorMessage);
    }
 }

Мой коллега с тех пор нашел ссылку на статью, в которой раскрывается возможность создания пользовательского связующего для модели, о котором я расскажу в будущем. Статья здесь и была первоначально найдена здесь.

Другие вопросы по тегам