.NET单元测试运行器输出FaultException.Detail

时间:2011-01-11 21:15:09

标签: wcf unit-testing mstest gallio xunit

我在WCF服务上运行一些单元测试。该服务配置为在故障响应中包含异常详细信息(在我的服务配置文件中包含以下内容)。

<serviceDebug includeExceptionDetailInFaults="true" />

如果测试导致服务器上出现未处理的异常,则客户端会使用完全填充的服务器堆栈跟踪来接收故障。我可以通过调用异常的ToString()方法来看到这一点。问题是,我尝试过的任何测试运行器(xUnit,Gallio,MSTest)似乎都没有输出。它们似乎只输出异常的Message和StackTrace属性。

为了说明我的意思,以下单元测试将输出三个部分:

  • 错误消息
  • 错误堆栈跟踪
  • 标准控制台输出(包含我想要的信息,例如“故障详细信息等于ExceptionDetail,可能由IncludeExceptionDetailInFaults = true创建,其值为:...”

public void Test()
{
    try
    {
        service.CallMethodWhichCausesException();
    }
    catch (Exception ex)
    {
        Console.WriteLine(ex); // this outputs the information I would like
       throw;
    }
}

编辑: 但是,我希望我不会在每个测试中捕获异常并将其写入控制台以确定{{1}内的内容对象的FaultException属性。

例如,

Detail

获得这些信息将使测试和部署的初始阶段不那么痛苦。

我知道我可以将每个单元测试包装在一个通用异常处理程序中并将异常写入控制台并重新抛出(如上所述)我的所有单元测试中但看起来似乎 实现这一目标的一种非常冗长的方式(看起来非常糟糕)。

有没有人知道在发生 未处理的 异常时是否有任何方法可以获取此信息?有没有我错过的环境?我的服务配置缺少正确的故障处理吗?也许我可以为某些单元测试框架编写某种插件/适配器?也许我应该使用不同的单元测试框架!

我的实际设置是通过Gallio为开发环境执行的xUnit单元测试,但我确实编写了一套单独的“冒烟测试”,我希望能让我们的工程师通过xUnit GUI测试运行runner(或Gallio或其他)简化最终部署。

感谢。

亚当

3 个答案:

答案 0 :(得分:1)

我想我找到了解决方案。 Oleg Sych已经实现了一个WCF行为,该行为透明地将异常从服务器封送到客户端,在客户端上提升它们就像它们在那里发生一样。

就像向服务合同(接口)添加服务行为属性一样简单。

如果确定编写为在单个进程内执行的现有代码应通过WCF服务分发,则此方法尤其有用。这意味着它可以在不需要对客户端的异常处理进行任何更改的情况下实现(例如,当您转向更分散的设计时,您仍然可以在客户端上处理SecurityException而不必处理FaultException<SecurityException> )。

可以在此处找到帖子:http://www.olegsych.com/2008/07/simplifying-wcf-using-exceptions-as-faults/

由于我的WCF服务使用了ws2007HttpBinding basicHttpBinding(用于互操作性)的混合,我不得不对代码进行一些更改(如上面帖子的评论中所述)。具体做法是:

ExceptionMarshallingMessageInspector.AfterReceiveReply

Exception exception = faultDetail as Exception;
if (exception != null)
{
    // NB: Error checking etc. excluded
    // Get the _remoteStackTraceString of the Exception class

    FieldInfo remoteStackTraceString = typeof(Exception).GetField(
        "_remoteStackTraceString",
        BindingFlags.Instance | BindingFlags.NonPublic);

    // Set the InnerException._remoteStackTraceString to the current InnerException.StackTrace
    remoteStackTraceString.SetValue(
        exception,
        exception.StackTrace + Environment.NewLine);

    throw exception;
}

...并在ExceptionMarshallingMessageInspector.ReadFaultDetail中进行了更改,以便查找本地名称等于“详细信息”的详细信息节点(对于ws2007HttpBinding“或”detail“(对于basicHttpBinding)。

我希望这会有所帮助。

亚当

答案 1 :(得分:0)

控制台输出在“测试结果”窗口中以列的形式提供。

答案 2 :(得分:0)

Gallio默认将控制台输出重定向到其诊断日志。因此,您应该直接在测试报告中看到所需的信息。

例如,在HTML报告的详细信息部分中,展开测试树并找到您的测试方法。

Console output in Gallio test report