【问题标题】:Error messages for model validation using data annotations使用数据注释进行模型验证的错误消息
【发布时间】:2010-05-11 19:52:14
【问题描述】:

给定以下类:

using System.ComponentModel.DataAnnotations;

public class Book{
   public Contact PrimaryContact{get; set;}
   public Contact SecondaryContact{get; set;}

   [Required(ErrorMessage="Book name is required")]
   public string Name{get; set;}
}
public class Contact{
    [Required(ErrorMessage="Name is required")]
    public string Name{get; set;}
}

有没有一种干净的方法可以使用DataAnnotationsBook 中的Contact 的每个实例提供不同的错误消息?例如,如果PrimaryContact 实例中缺少姓名,则错误将显示为“需要主要联系人姓名”。

我当前的解决方案是创建一个验证服务来检查模型状态中的字段错误,然后删除所述错误并使用我想要的特定语言将它们添加回来。

【问题讨论】:

    标签: c# asp.net-mvc validation annotations data-annotations


    【解决方案1】:

    这是我知道的唯一方法,但它远非干净。它涉及使用子类和 MetaData 类来“覆盖”错误消息。

    public class Book
    {
        public PrimaryContact PrimaryContact { get; set; }
        public SecondaryContact SecondaryContact { get; set; }
    
        [Required(ErrorMessage = "Book name is required")]
        public string Name { get; set; }
    }
    
    public class Contact
    {
        [Required(ErrorMessage = "Name is required")]
        public string Name { get; set; }
    }
    
    [MetadataType(typeof(PrimaryContactMD))]
    public class PrimaryContact : Contact
    {
        class PrimaryContactMD
        {
            [Required(ErrorMessage = "Primary Contact Name is required")]
            public string Name { get; set; }
        }
    }
    
    [MetadataType(typeof(SecondaryContactMD))]
    public class SecondaryContact : Contact
    {
        class SecondaryContactMD
        {
            [Required(ErrorMessage = "Secondary Contact Name is required")]
            public string Name { get; set; }
        }
    }
    

    【讨论】:

      【解决方案2】:

      您可能希望考虑将CustomValidation 属性用于此类属性,而不是依赖Required 属性。

      CustomValidation 将允许您更细致地针对您正在验证的属性定制验证消息。为了简洁起见,我使用context.DisplayName 动态显示正在验证的属性的名称,但这可以根据您的需要进一步定制。

      如果需要进一步自定义,您可以为每个单独的属性编写不同的 CustomValidation 处理程序,而不是像我在代码示例中那样重复使用相同的处理程序。

      using System.ComponentModel.DataAnnotations;
      
      public class Book {
          [CustomValidation(typeof(Book), "ValidateContact")]
          public Contact PrimaryContact { get; set; }
      
          [CustomValidation(typeof(Book), "ValidateContact")]
          public Contact SecondaryContact { get; set; }
      
          [Required(ErrorMessage = "Book name is required")]
          public string Name { get; set; }
      
          public static ValidationResult ValidateContact(Contact contact, ValidationContext context) {
              ValidationResult result = null;
      
              if (contact == null) {
                  result = new ValidationResult($"{context.DisplayName} is required.");
              } else if (string.IsNullOrWhiteSpace(contact.Name)) {
                  result = new ValidationResult($"{context.DisplayName} name is required.");
              }
      
              return result;
          }
      }
      
      public class Contact {
          [Required(ErrorMessage = "Name is required")]
          public string Name { get; set; }
      }
      

      【讨论】:

        【解决方案3】:

        我也在寻找这个问题的答案,到目前为止,如果您在错误消息中执行以下操作:“{0} 联系人姓名是必需的”,它将自动替换变量的名称。我认为有一种方法可以显式使用此功能。

        【讨论】:

          【解决方案4】:

          下面的c#代码格式化数据注释错误并在单个字符串中追加格式

            public class ValidateModelAttribute : ActionFilterAttribute
              {
                  public override void OnActionExecuting(HttpActionContext actionContext)
                  {
                      if (actionContext.ModelState.IsValid == false)
                      {
                          if (actionContext.ModelState.IsValid) return;
                          string errors = actionContext.ModelState.SelectMany(state => state.Value.Errors).Aggregate("", (current, error) => current + (error.ErrorMessage + ". "));
                      }
                  }
              }
          

          【讨论】:

          • 请不要只发布代码作为答案,还要解释您的代码的作用以及它如何解决问题的问题。带有解释的答案通常更有帮助、质量更好,并且更有可能吸引投票
          猜你喜欢
          • 2023-03-27
          • 1970-01-01
          • 1970-01-01
          • 2013-02-10
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 2023-03-13
          相关资源
          最近更新 更多