是否应该在商业模式或视图模型上进行验证?

时间:2011-09-23 14:43:29

标签: validation n-tier-architecture

我想弄清楚在我的N-Tier Asp.net MVC应用程序中放置验证的位置

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

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

第三个选项是在业务对象和视图模型之间拆分验证。这个问题是我可以看到,如果由于视图模型验证失败或业务对象验证失败而触发验证规则,则很难实现。

2 个答案:

答案 0 :(得分:2)

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

我会保证查看和业务层。在向服务器发送请求之前,有些事情可以在视图层中捕获。例如,在上传100 MB大文件之前检查是否存在字段验证错误是有意义的,只是告诉用户他们输入了错字。显然,视图验证应始终由服务器端验证进行备份。

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

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

我希望这会有所帮助。

答案 1 :(得分:1)

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

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

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