具有许多不同类型错误的业务组件

时间:2009-08-31 22:55:23

标签: language-agnostic error-handling

这只是一个一般性的设计问题。如果您正在开发业务组件或服务(例如,公开用于处理计费事务的相对简单的接口的对象/服务),处理与业务相关的错误的一些好方法是什么?

假设组件/服务必须与几个不同的外部Web服务集成,这些服务都报告不同的错误,并且还必须在您身边执行一些数据库工作。有许多不同的东西可能出错,无论是网络/数据库方式还是业务规则方面。尝试捕获组件中的所有类型的错误并使用错误代码方案将它们报告给调用者,或尝试将所有错误包装到各种类型的异常中并将它们抛给调用者是否会更好?

这似乎很难,因为使用异常来处理业务规则检查变得很尴尬,而且我已经在几个地方读过以避免使用异常来控制“非异常”或业务逻辑流程。我认为“特殊”通常是一个值得商榷的术语,并且试图将不同的案例定义为“特殊”与“非特殊”之间的关系变得棘手。 (例如,如果您的业务逻辑检查支出限制,年龄限制等)。同时,使用错误代码方案也很尴尬,因为调用者可能会选择忽略错误代码。

任何提示或参考将不胜感激!

4 个答案:

答案 0 :(得分:1)

我会选择错误代码方案,因为你说“许多不同的东西都可能出错”。您可能希望有一个返回Error对象列表的方案,其中Error将封装代码,解释,原始数据等。

异常只能说明一件事是错的,它应该具有“特殊”性质,而不是普通的问题。

或者也许是一个混合,你抛出一个异常,它有一个Error对象列表作为私有数据成员,以及一个允许你迭代错误的访问方法。

答案 1 :(得分:1)

与业务相关的错误不应该是exeptions。如果程序中存在程序不能处理或完全不可预测的事件,则存在例外情况。 为此,如果您预期会有大量不同的异常,请务必实施一些有用的编号方案。在这里,我会推荐一个guid,因为组件重用的原因。每个组件都应该公开一些接口来查询可能的异常编号列表(然后可以将其添加到数据存储区以获取文档)。此外,当您重用组件时,错误代码不会发生冲突。

另一方面,用户或业务数据错误几乎保证了一些编号方案。 几乎没有办法预测用户能够做的所有愚蠢的事情。但是,我强烈反对支持某些自定义错误对象的正式语言异常。语言异常可能会产生很大的开销,或者需要专门的处理来防止它们传播调用堆栈。业务错误对象可能是一个很好的方法。

答案 2 :(得分:1)

服务是临界的,特别是如果必须使用可能无法正确处理SOAP异常的各种语言。如果它出现在WWW上也存在安全问题。

如果它不是服务,是内部的,和/或将由已知语言的客户端访问,请使用异常来处理故障情况。客户无法保证检查错误代码。

请参阅 http://msdn.microsoft.com/en-us/library/ms229030.aspx 对此进行了很好的讨论。 (这也在书中Framework Design Guidelines。)

答案 3 :(得分:1)

绝对没有任何东西可以阻止您同时制定业务规则和技术规则违规。我在两种情况下使用例外:

  1. 违反前提条件。如果您的函数规范说“花费的金额不应超过此类帐户的限制”,并且用户知道此,则指定更大的限制,将异常抛给他!

  2. 违反后置条件。如果满足所有先决条件,但由于意外拒绝(例如数据库连接;或者交易完成违反了反垄断法),则无法提供正确的结果,请勿提供。抛出异常。

  3. 由于所有业务逻辑可能都在一个组件内,并且不依赖于其他任何内容,因此业务异常的案例2非常少见。应该在前端应用程序中检查属于案例1的内容。这让我觉得不抛出业务逻辑异常的方法并不是你“不应该”,而是“你大部分都不需要”。

    无论如何,从您编程的语言的角度来看,它几乎没有注意到“技术”和“业务”异常之间的区别,因此它将正确处理它们。其次,异常被捕获到某处。我想,从架构师的角度来看,业务和技术异常将被捕获在不同的组件中。当然,除非它们实际上没有被捕获,否则只显示没有编程处理的错误消息属于这一类。因此,使用相同的机制不会让你混淆这些错误。

    所以,我的观点是,如果您选择不将异常作为编程概念来排斥,那么您也可以将它们用于业务逻辑。