Asp.net-MVC自定义验证-空与空

本文关键字:验证 net-MVC 自定义 Asp | 更新日期: 2023-09-27 18:20:30

为了安全性和一致性,如果缺少字段,我想在后台测试?在Java(特别是servlet)中,当我们执行request.getParameter(key)时,结果要么是String值,要么是NULL(如果字段丢失)。在MVC中,我创建了一个自定义验证,称之为"ThrowOnNull"。我试图捕捉的行为是:如果想要抛出的字段丢失(null),否则返回success。

考虑一下这个自定义验证器(不起作用):

public class ThrowOnNull: ValidationAttribute
{
   public ThrowOnNull() { }
   protected override ValidationResult IsValid(object value, ValidationContext validationContext)
   {            
       if (value == null)
           throw new Exception(validationContext.MemberName + " field expected, but missing."));            
       return ValidationResult.Success;
   }
}

有可能在这里做我想做的事吗(这个验证器没有按预期工作,这是因为框架正在将NULL分配给一个空值[哦,亲爱的]。)

UPDATE:根据@emodendroket,以下代码示例现在可以按预期工作:

public class ThrowOnMissing: ValidationAttribute
{
    public ThrowOnMissing() { }
    protected override ValidationResult IsValid(object value, ValidationContext validationContext)
    {
        if (!HttpContext.Current.Request.Form.AllKeys.Contains(validationContext.MemberName))
            throw new Exception(validationContext.MemberName + " field expected, but missing.");
        return ValidationResult.Success;
    }
}

EDIT:我已经对问题和示例代码进行了大量清理,使其更加清晰,希望它能有所帮助。

Asp.net-MVC自定义验证-空与空

您缺少一个重要的点-当您提交表单时,属于该表单的所有字段都会被提交。如果用户不填写它们,它们就是空白的,所以null的验证不能像这样工作。。。

您可能应该重新定义"缺失值"的含义。

编辑:
经过一番讨论,您似乎并不真正关心null值,而是关心安全性(带有缺失字段的虚假表单等)。在这种情况下,您应该简单地使用标准的防伪造令牌,并可能检查请求的来源。这样你应该很好。检查丢失的字段不会有任何帮助,因为攻击者也可以很容易地发送这些字段。

发帖过多/过少是一个真正令人担忧的问题。此外,如果字段没有提交(由于某种黑客攻击或DOS攻击)

不是。

通过控制器上的动作方法来处理溢出。它不会接受超过您指定的参数。

如果您没有填写表单中的文本字段,则会以几乎相同的方式处理欠报,如果您正确验证了您的模型,这也是一个问题。

DDOS攻击是无法阻止的——相信我,如果有人拥有足以引发DDOS的强大网络,那么一些缺失字段的检查将毫无帮助。只要查看最新的攻击案例,你就会明白,如果庞大的服务器无法承受这种攻击,你肯定无法像这样阻止它。

您的数据验证也不应该太昂贵。这是一个网络,人们不喜欢等太久。

如果您想要自己的验证器,可以查看字典HttpContext.Current.Request.Form。然后你可以用这个代码做你建议的事情:

if (!HttpContext.Current.Request.Form.AllKeys.Contains("prop"))
  {
    throw new Exception();
  }

我认为你在这里对事情过于偏执。注意,我说的是不合理的偏执狂,因为有点偏执是件好事。

首先,让我们分析"威胁"并确定风险。你已经提出了几个论点:

  1. 超额过帐
  2. 正在过帐
  3. 空与空的验证

如果您使用的是视图模型,那么第一项在MVC中不是问题。您根本无法发布视图不期望的信息(当然可以,但它被忽略了)。如果未使用视图模型(或未使用正确定义的视图模型),则可以使用绑定属性来防止发布不希望绑定的项目。

第二次,在张贴中,如果这真的是你的模特关心的问题(99.999%的情况下,简单地将其视为需要是很好的,但好吧,让我们接受你的论点。这里的问题不是验证属性,而是模型绑定器。你只需要注册一个自定义模型绑定器,它可以在视图模型中查找缺失的值,并在它们为空时抛出。这很容易通过反映绑定模型并将其与发布的模型进行比较来实现值,然后抛出。

你的RequiredSthrowIfNull方法的问题是……如果它不是必需的,并且发布不足怎么办?根据你的论点,这仍然是个错误。

最后,验证空与空。。。你说昂贵的验证。。。我不知道你在这里谈论的是什么样的昂贵的验证,但服务器端的属性中有一点可能被认为是昂贵的。

属性不起作用的原因是,框架已经在try/catch块中调用了验证属性,如果它为null,则正是将其视为空的机制(该机制还可以在类型不正确时捕获解析错误,例如日期时间字段中的字符)

.NET不是Java,尽管它在很大程度上是类似的。。。试图在.NET中重新实现Java模式会给你带来痛苦,因为许多基本的哲学都是不同的。

即使我们接受你的论点,即想要发现错误或收到黑客攻击的通知,在大多数情况下,投掷也是错误的。相反,只需记录模型绑定器中的信息,然后继续正常操作。只有在你绝对需要中止请求的情况下才抛出,大多数时候情况并非如此,即使你被黑客入侵。。。投掷只会导致攻击者改变他们的攻击,直到他们不再得到异常。

坦率地说,这是一个过度设计的、寻找问题的解决方案,有很多好的.net特定的方法来处理你试图解决的真实问题。来自ASP.NET

@ignatandrei回答了以下问题:

默认情况下,MVC将空字符串转换为空字符串。

http://forums.asp.net/t/2006146.aspx?Custom+验证+和+NULL