在数据注释验证错误消息中隐藏基础属性名称

时间:2019-05-05 14:16:40

标签: c# asp.net asp.net-core

我有这个asp.net核心模型:

public class MyModel
{
    [ModelBinder(Name = "id")]
    [StringLength(36, MinimumLength = 3)]
    public string ObjectId { get; set; }
}

我添加了ModelBinder属性,以便将“ ObjectId”字段重命名为“ id”。

当我尝试使用错误的值提交模型时。例如:

{
    "id": "1111111111111111111111111111111111111111111111111111111111111111111111111111"
}

我正在从服务器获取此响应:

{
     "id":["The field ObjectId must be a string with a minimum length of 3 and a maximum length of 36."]
}

预期输出:

{
     "id":["The field id must be a string with a minimum length of 3 and a maximum length of 36."]
}

这很奇怪,因为key(“ id”)是用正确的大小写写的。但是在value(“ ObjectId”)中,它被写错了。

我的客户不应该知道ObjectId。他只知道id。如何修复此类消息?

谢谢。

3 个答案:

答案 0 :(得分:1)

解决方案是使用DisplayName属性:

public class MyModel
{
  [ModelBinder(Name = "id")]
  [StringLength(36, MinimumLength = 3)]
  [DisplayName("id")]
  public string Id {get; set;}
}

答案 1 :(得分:0)

您可以在StringLengthAttribute Class上设置自定义错误消息。

public class MyModel
{
    [ModelBinder(Name = "id")]
    [StringLength(36, MinimumLength = 3, ErrorMessage="The field id must be a string with a minimum length of {1} and a maximum length of {2}.")]
    public string ObjectId { get; set; }
}

文档页面摘录:

  

您可以在错误消息中使用复合格式的占位符:{0}是属性的名称; {1}是最大长度; {2}是最小长度。占位符对应于在运行时传递给String.Format方法的参数。

答案 2 :(得分:0)

对于StringLength,它使用默认属性名称来构造预期的错误消息。

如果您更喜欢使用Name的{​​{1}}标签,则可以像

那样实现自己的ModelBinder进货
StringLength

然后像

一样使用它
public class CustomStringLength : StringLengthAttribute
{
    public CustomStringLength(int maximumLength) 
        : base(maximumLength)
    {
    }
    public override string FormatErrorMessage(string name)
    {

        return base.FormatErrorMessage(name);
    }
    protected override ValidationResult IsValid(object value, ValidationContext validationContext)
    {
        var propertyName = validationContext.DisplayName;
        var propertyAttribute = validationContext.ObjectType
                                    .GetProperty(propertyName)
                                    .GetCustomAttribute(typeof(ModelBinderAttribute));
        if (propertyAttribute is ModelBinderAttribute modelBinderAttribute)
        {
            validationContext.DisplayName = modelBinderAttribute.Name;
        }
        //validationContext.DisplayName = "Id";
        return base.IsValid(value, validationContext);
    }
}