SOAP错误或结果对象?

我正在和一个同事讨论这个问题,我们不能达成一致,所以我想说说你的想法。 我对此有我自己的看法,但我不会为你破坏它。

什么时候应该返回一个SOAP错误 ,什么时候应该返回一个有错误信息的结果对象 ? 假设这是一个通用的Web服务,可以被各种系统(.NET,Java等)使用。 结果对象将有一个isError标志,一个errorType(类似于特定的exceptiontypes)和一个消息。

有几点需要考虑:

  1. 数据validation错误是一个错误?
  2. 是否有一个错误组合(对于非常特殊情况)和结果对象(对于“预期”错误)?
  3. 你将如何分组SOAP错误(关键[空引用]与validation[邮政编码不正确])?
  4. 快速失败vs必须记住检查错误
  5. 最佳做法,模式,标准等

链接到文章是有效的。 即使这听起来像我想要你的意见, 请坚持事实 (X是更好的,因为Y和Z …)

大多数SOAP客户端会将错误转换为运行时exception(如果这是客户端语言支持的)。 考虑到这一点,我想你可以把这个问题改为“我什么时候想抛出exception而不是返回一个错误值”? 我相信你可以find关于这个APIdevise的大部分意见,特别是这个话题。

也就是说,返回一个错误通常对客户没有帮助:

  1. 客户端需要手动枚举和处理您的错误代码,而不是允许存根代码生成并抛出相应types的exception。 使用错误代码可以防止客户端使用面向对象的技术,如通过超类来处理exception。

  2. 如果您不将错误代码作为WSDL的一部分; 客户将没有关于它们是什么或何时发生的文档。 types错误是WSDL的一部分,因此(在某种程度上)自我logging。

  3. 故障消息可以包含客户机可用于错误报告和恢复的故障特定上下文。 例如,抛出包含实际无效input元素和原因的inputvalidation错误。 如果返回错误代码和不透明string的结果,客户没有多lessselect,只能将错误消息传递给用户,这打破了国际化,UI一致性等等。

回答你的具体问题:

  1. validation错误是一个错误。 想象一下,如果您从AJAX客户端调用Web服务,并具有有限的error handling能力, 您希望该服务返回一个5xx HTTP代码,而不是一个400意外的响应成功的代码。

  2. 编号API应提供一致的错误报告界面。 WSDLdevise是APIdevise。 强制客户端实现两个不同的error handling程序不会使客户端的生活更轻松。

  3. 错误devise应该反映你的请求/响应模型,并显示适合抽象服务的信息。 不要devise一个NullReference错误; devise一个XYZServiceRuntimeFault。 如果客户端经常提供无效的请求,请devise一个InvalidRequestFault,并带有适当的子类,以便客户端可以快速找出无效数据的位置。

结果对象应该只包含结果。 如果你的结果对象提供了在另一个系统上发生的错误列表,那么你就可以拥有和“isError”标志的例子。 否则你不能因为结果是有效的或没有。

发生错误时应始终使用SOAPFault。 validation是一个错误,这是魔鬼自己的陷阱,认为validation不比无法打开数据库严重。 两种情况都有相同的影响 – 操作无法按要求完成。

所以你应该使用结果对象的结果和SOAP错误来阻止任何有效的结果对象。 包括但不限于错误,validation失败,警告,总线故障等。

在exception之前的日子里,没有select,因此许多API变得不一致,大多数API在如何返回错误方面有所不同。 这是(现在仍然)是可怕的,令人困惑,并且往往放缓开发,因为你必须查找每个API条目如何返回一个错误,并经常如何解码或找出更多的错误。

  1. 使用SOAPFaults / Exceptions处理validation在您思考时更为合理,一旦您想到了,通常会更容易。 您确实需要devisevalidation错误类,以便它包含足够的信息,以不一定要求原始请求的方式识别违规元素。 这样你就可以开始更一般地处理validation错误。

  2. 如果结果对象包含错误,则它们只能在结果的域中; 例如产品缺货,因为在仓库里有人不能计数是在库存控制范围之内。

  3. 区分一个严重错误和一个validation错误是不明智的,在我看来这不是一个有效的比较,因为任何严重级别的分配都是非常主观的。 例如,在向消防员提供有关化学品的信息的系统中,危急可能意味着,当试图加载警告图时,着火的卡车携带UN 1298和UN 1436,而不是空引用。

    devise错误,使其能够被简明扼要地识别和处理。 确保他们传达足够的信息。 当您获得足够的信息时,概念分类是无意义的,因为故障将允许自己被识别。

  4. SOAPFaults变成exception是确保快速失败的最可靠的方法。

  5. 最佳实践,参考文献等

    • pipe理SOA世界中的exception:Ramesh Ranganathan

    • 当例外是规则:实现可靠和可跟踪的面向服务的体系结构

    • SOAP故障的最佳实践

    • 使用SOAP Faults在开发时向开发人员提供适当级别的细节,在Web服务正在生产时向客户提供适当级别的细节。

    • Web服务使用SOAP故障将故障情况报告给客户端。 如果SOAP消息无效,安全令牌无效,或者可以从服务业务逻辑本身生成错误

    • 如果您发送的消息由于某种原因而不成功,您可能会收到一个包含SOAP错误元素的响应,该元素可以为您提供状态信息,错误信息或两者。 消息中只能有一个SOAP错误元素,并且它必须是SOAP正文中的一个条目。 而且,如果SOAP正文中存在SOAP错误元素,则SOAP正文中不能包含其他元素。 这意味着当你添加一个SOAP错误元素时,你已经有效地完成了SOAP主体的构造。

    • SOAP错误消息是SOAP应用程序向消息path中较早的节点“上游”报告错误的机制。 本节的任务是提供关于SOAP错误的完整和详细的解释,以便您可以在自己的Web服务中适当地处理它们。

我认为简短的答案是使用肥皂故障,除非您知道客户端将配备处理由此返回的错误。 正如其他答案中提到的,我也在思考exception和错误结果之间的类比。

有灰色地带可以合理地视为例外,并根据客户的需要作为结果错误。 然后,您可能会向该服务提供一个参数,以改变这些types的错误返回的方式。 缺省情况是使用SOAP错误,但是如果客户端设置参数以获得错误结果,则表示它愿意将其作为结果的一部分处理。 对我来说,validation错误在这个灰色地带。 对于大多数客户来说,他们应该被视为错误,但是如果客户想要使用这些数据来标记带有validation错误的UI,那么作为结果的一部分返回validation错误可能会更有用。

我在服务devise中遵循的规则是:

  • 业务级响应(甚至业务exception)到响应对象中
  • 技术/集成水平错误到Soap Fault

服务消费者可以依靠所有types的业务响应来响应对象,并将其呈现给服务(业务)用户。 Soap Faults仅在业务响应无法传递时使用。

Soap Faults应该通过监控引发支持警告/行动。