实现自定义 ValidationAttribute 时我应该重写哪个 IsValid 方法

问题描述 投票:0回答:2

当我实现从 ValidationAttribute 类继承的自定义属性时,我总是覆盖

bool IsValid(object value)
方法而忽略另一个原型为
ValidationResult IsValid(objet value, ValidationContext validationContext)
的方法。

也许,即使我不使用验证上下文或结果(我将验证与 EntityFramework 和

ModelState.IsValid
控制器属性一起使用),我也应该覆盖第二种方法。或者继续无视重载的方法。如果那样的话,我能否根据调用属性验证的上下文使对象有效或无效?如下代码所示的情况是否有问题?

class StrictlyPreviousAttribute : ValidationAttribute
{
    public override bool IsValid(object value)
    {
        var dateTime = value as DateTime?;
        return dateTime == null || dateTime <= DateTime.Today;
    }
}

class PreviousAttribute : StrictlyPreviousAttribute 
{
    public override ValidationResult IsValid(object value, ValidationContext validationContext)
    {
        var dateTime = value as DateTime?;

        if(dateTime == DateTime.Today)
        {
            return ValidationResult.Success;
        }
        else
        {
            return base.IsValid(object);
        }
    }
}

我不知道是否存在对象误解或者我是否遗漏了一些要点。有没有一种方法我应该优先覆盖而不是其他方法。我应该覆盖两者吗?

.net entity-framework validation attributes
2个回答
5
投票

Steve Greene 在上面的评论中提供的链接启发了方法之间的区别并回答了问题。

返回

bool
的方法仍然存在以实现向后兼容性,但自 .NET 4.0 以来不再是抽象的。建议覆盖有权访问
ValidationContext
.

的方法

这(除其他外)给了我们 即使验证器位于属性中,也可以访问整个模型 等级。使用属性级别验证器的巨大优势是 错误是针对属性本身而不是类设置的 删除使用 Html.ValidationSummary 的要求。自从 针对该属性正确设置了验证错误,您的正常 Html.ValidationFor Html.ValidationMessageFor 助手将拾取并显示错误 无效的表单字段。

它是不久前编写的(使用 ASP.NET MVC 3),但对于 .NET 4.6 框架仍然有效。此外,我还为

bool IsValid(object value)
方法实施了单元测试。即使我只使用
ValidationContext
参数覆盖方法,测试也会继续通过。


0
投票

根据 reference source,返回 bool 的重载已被弃用,您应该只覆盖采用 ValidationContext 的重载:

        /// Derived classes should not override this method as it is only available for backwards compatibility.
        /// Instead, implement <see cref="IsValid(object, ValidationContext)"/>.

不幸的是,在撰写本文时,该弃用评论尚未进入文档。

© www.soinside.com 2019 - 2024. All rights reserved.