【问题标题】:Should validation be on business models or view models?验证应该针对业务模型还是视图模型?
【发布时间】:2011-09-23 14:43:29
【问题描述】:

我正在尝试找出在我的 N 层 Asp.net MVC 应用程序中放置验证的位置

一方面,我觉得验证应该与业务对象本身一起在业务层中进行。这意味着当验证规则发生变化时,我只需在一个位置进行更改(例如,现在用户显示名称可以是任何内容,但现在我希望名称至少包含 5 个字符且没有符号)。这使得了解在哪里可以找到验证规则变得很容易,并且更容易在各个流程中保持验证规则的一致性。

另一方面,我也觉得验证应该在视图模型上进行,因为有时您需要对业务对象不需要的特定流程数据进行验证。例如,当用户更改密码时,您希望他们在表单中输入密码两次,这样他们就不会输错密码而导致登录失败。您的 User 业务对象不需要两个密码字段,因为它没有意义,因为您在更改当前密码(或创建新帐户)时只需要两个密码。因此,对我来说将验证放在视图模型上以确保运行特定于流程的验证是有意义的。这样做的缺点是,当验证规则发生变化时,您可能会出现很多需要更新的地方(您必须更改每个与用户打交道的视图模型的规则)。

第 3 个选项是在您的业务对象和视图模型之间拆分有意义的验证。这样做的问题是,我发现很难意识到是否由于视图模型验证失败或业务对象验证失败而触发了验证规则。

【问题讨论】:

    标签: validation n-tier-architecture


    【解决方案1】:

    您已经做了一些很好的考虑。就个人而言,我之前在视图和控制器层中进行了验证,但最近意识到这可能不是最好的方法。虽然在控制器中执行此操作确实有意义,但正如您也提到的,它确实可以成为一项重复性任务。

    我保证视图和业务层。在向服务器发送请求之前,在视图层中捕获某些东西是很好的。例如,在上传 100 MB 大文件之前检查是否存在字段验证错误只是为了告诉用户他们犯了错字是有意义的。显然,视图验证应该始终得到服务器端验证的支持。

    被称为“胖模型”的概念将尽可能多的验证放在业务层中,这有很多优点;

    • 您的代码将可重复使用,因为它将被包装在每个业务对象中,而不是用于特定的控制器操作。如果您需要更新业务规则,那么您只需要更新相关模型,而不是每个使用这些模型的控制器(您自己也提出了一个很好的观点)
    • 您的代码将更具可移植性,因为它更容易切换到不同的框架,例如,如果您没有依赖控制器来执行业务逻辑的业务层
    • 控制器将更容易理解,因此为什么您的应用程序中的流程更容易遵循,新开发人员可能会发现更容易上手
    • 编写一两次验证规则比重复编写错误电话更少
    • 调试和测试可能会更容易

    我希望这会有所帮助。

    【讨论】:

      【解决方案2】:

      我推荐您的第三个选项。根据需要拆分验证。

      使用您输入两次新密码的示例(以确保输入正确),将两个密码都发送到业务模型(特别是如果这是一个分布式/Web 应用程序)以检查它们是否正确是没有意义的是相同的,当您的视图模型可以轻松地比较两者时。其他限制条件,如用户名长度或留空的必填字段,可以在输入时在视图中轻松检查,并向用户提供即时反馈。
      有些东西在视图模型中无法验证,需要传递给业务模型进行检查。一个例子是用户名的唯一性。
      需要考虑的一件事是(尤其是在 Web 开发中),客户端验证更容易绕过,因此即使实现了它,恶意/恶作剧的用户仍然可以设法提交不良数据。为了涵盖这种情况,最好在服务器端检查任何关键的验证约束。当然,这又回到了导致你提出这个问题的不太干燥的问题......

      编辑
      我建议进行任何分离的主要原因是为用户提供即时反馈,以便他们可以在实际提交给服务器进行处理之前根据需要修复他们的提交。如果您的困境是在一个服务器端位置和另一个放置验证代码的位置之间,那么我说这是个人喜好问题,但我建议不要将其分开。在这种情况下,最好将所有内容保存在一个有凝聚力的地方,这样您就可以确切地知道去哪里进行更新和错误修复。

      【讨论】:

      • 通过检查 ViewModel 我仍然在谈论检查服务器端。
      • 好吧,那样的话,我上次提的问题基本上是无关紧要的。
      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2011-05-26
      • 1970-01-01
      • 2010-11-18
      • 2010-11-18
      • 2011-04-04
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多