我们目前正在争论是否最好在WCF频道上抛出错误,而不是传递指示服务状态或响应的消息。
故障来自WCF的内置支持,您可以使用内置的错误处理程序并做出相应的反应。然而,这会带来开销,因为在.NET中抛出异常可能会非常昂贵。
消息可以包含必要的信息,以确定服务调用发生的情况,而不会产生抛出异常的开销。但是,它确实需要几行重复代码来分析消息并确定其内容后面的操作。
我们开始创建一个我们可以在服务中使用的通用消息对象,这就是我们提出的:
public class ReturnItemDTO<T>
{
[DataMember]
public bool Success { get; set; }
[DataMember]
public string ErrorMessage { get; set; }
[DataMember]
public T Item { get; set; }
}
如果我的所有服务调用都返回此项,我可以一直检查“成功”属性以确定是否一切顺利。然后我在事件中有一个错误消息字符串表示出现了问题,并且在需要时包含Dto的通用项目。
异常信息必须记录到中央记录服务,而不是从服务传回。
思考?评论?想法?建议
对我的问题进一步澄清
我遇到的与错误合同有关的问题是沟通业务规则。
例如,如果有人登录,并且他们的帐户被锁定,我该如何沟通呢?他们的登录显然失败了,但由于“帐户锁定”的原因而失败。
我也是这样:
A)使用布尔值,抛出错误消息帐户锁定
B)返回带有相关信息的AuthenticatedDTO
答案 0 :(得分:31)
然而,这会带来开销,因为在.NET中抛出异常会非常昂贵。
您将对象序列化并反序列化为XML并通过慢速网络发送它们。抛出异常的开销与此相比可以忽略不计。
我通常坚持抛出异常,因为他们清楚地传达了出错的地方,所有 webservice工具包都有一个很好的方法来处理它们。
在你的示例中,我会抛出一个UnauthorizedAccessException并显示“Account Locked”消息。
澄清:默认情况下,.NET wcf服务会将异常转换为FaultContracts,但您可以更改此行为。 MSDN:Specifying and Handling Faults in Contracts and Services
答案 1 :(得分:6)
如果你考虑像调用任何其他方法一样调用服务,它可能有助于把事情放在眼里。想象一下,如果您调用的每个方法都返回了一个状态,那么您需要检查它是真还是假。这会非常繁琐。
result = CallMethod();
if (!result.Success) handleError();
result = CallAnotherMethod();
if (!result.Success) handleError();
result = NotAgain();
if (!result.Success) handleError();
这是结构化错误处理系统的优点之一,您可以将实际逻辑与错误处理分开。您不必继续检查,如果没有抛出异常,您就知道它是成功的。
try
{
CallMethod();
CallAnotherMethod();
NotAgain();
}
catch (Exception e)
{
handleError();
}
同时,通过返回结果,您将对客户承担更多责任。您可能知道检查结果对象中的错误,但是John Doe进来并且刚开始调用您的服务,忘记了任何错误,因为没有抛出异常。这是另一个例外的强项,就是当出现问题并需要照顾时,它们会给我们一个好的耳光。
答案 2 :(得分:0)
我会认真考虑使用FaultContract和FaultException对象来解决这个问题。这将允许您将有意义的错误消息传递回客户端,但仅在发生故障时才会发送。
不幸的是,我现在正在参加培训课程,因此无法写出完整的答案,但幸运的是,我正在学习WCF应用程序中的异常管理。今晚我会回复更多信息。 (对不起,这是一个微弱的答案)