抛出异常后的单元测试行为?

Jon*_*Jon 3 tdd nunit unit-testing rhino-mocks exception-handling

我刚刚开始进行单元测试并且有一个场景我不知道如何评估和我的解决方案感觉不对.

我有一些代码可以执行某些操作,如果失败,则抛出异常,捕获并记录异常,如下所示.

 public T CreateTypedObjectInstance<T>()
 {
     T o = default(T);
     try
     {
         o = Activator.CreateInstance<T>();
     }
     catch (Exception ex)
     {
         LogError(ex);
         throw ex;
     }
     return o;
 }

 private void LogError(Exception ex)
 {
     if (logger != null)
     {
        logger.LogError(ex);
     }
 }
Run Code Online (Sandbox Code Playgroud)

我想测试一下,如果抛出错误,它会调用LogError()方法,后者又调用另一个对象.

我使用了一个模拟记录器来处理这个问题并捕获抛出的第一个异常,然后断言调用了LogError方法.但是,这不需要捕获异常吗?我记得读过一些在测试中尝试捕获的东西是不好的吗?有没有其他方法可以执行此测试,还是应该重构逻辑?任何想法都会很棒!

      [Test]
    public void CreateTypedObjectInstance_GivenTypeWithoutPrivateContructor_LogErrorToLogger()
    {
        //Setup Method used
        MockRepository mockery = new MockRepository();
        ILogger mockedLogger = mockery.StrictMock<ILogger>();
        genericObjectFactoryInstance.Logger = mockedLogger;
        Expect.Call( delegate { mockedLogger.LogError(null); } ).IgnoreArguments();
        mockery.ReplayAll();
        // this will throw an error as String does not have a parameterless constructor
        try
        {
            genericObjectFactoryInstance.CreateTypedObjectInstance<String>();
        }
        catch { /*ignore this error to test behaviour after*/ }
        mockery.VerifyAll();
    }
Run Code Online (Sandbox Code Playgroud)

编辑

使用Mark Rushakoff回答测试成为一种魅力.

        [Test]
    public void CreateTypedObjectInstance_GivenTypeWithoutPrivateContructor_LogErrorToLogger()
    {
        //Setup Method used
        MockRepository mockery = new MockRepository();
        ILogger mockedLogger = mockery.StrictMock<ILogger>();
        genericObjectFactoryInstance.Logger = mockedLogger;
        Expect.Call( delegate { mockedLogger.LogError(null); } ).IgnoreArguments();
        mockery.ReplayAll();
        Assert.Throws<MissingMethodException>(() => genericObjectFactoryInstance.CreateTypedObjectInstance<String>());
        mockery.VerifyAll();
    }
Run Code Online (Sandbox Code Playgroud)

Mar*_*off 7

您没有说明您正在使用的NUnit版本,但首选方法是该Assert.Throws方法.

Assert.Throws<YourCustomException>(() => GenericObjectFactoryInstance.CreateTypedObjectInstance<String>());
Run Code Online (Sandbox Code Playgroud)

当您的测试框架没有提供检查抛出异常的工具时,@ Bruno的答案是合适的.