简体   繁体   English

Junit4:expected =异常无法使用SPRING

[英]Junit4 : expected=Exception not working with SPRING

I'm trying to use the @Test(expected = RuntimeException.class) annotation in order to test for an expected exception. 我正在尝试使用@Test(expected = RuntimeException.class)注释来测试预期的异常。 My code is as follows: 我的代码如下:

@Test(expected = RuntimeException.class)
    public void testSaveThrowsRuntimeException(){

                    User user = domain.save(null);

    }

and my save method simple like this : 和我的保存方法简单如下:

public User save(User newUser) { 
         if(newUser == null) { 
            throw new RuntimeException(); 
         }
         //saving code goes here
    }

after debugging the code I found that code throwing the exception as expected but its getting eaten somewhere in between in spring framework classes. 在调试代码之后,我发现代码抛出了预期的异常,但它在spring框架类之间的某处被吃掉了。

I tried the same with old way (try catch block) but still I am not able to catch that exception in test and test keeps throwing errors in runafter method of Junit : 我尝试使用旧方法(尝试catch块)但仍然无法在测试中捕获该异常并且测试在Junit的runafter方法中不断抛出错误:

org.springframework.transaction.UnexpectedRollbackException: JTA transaction unexpectedly rolled back (maybe due to a timeout); nested exception is javax.transaction.RollbackException
at org.springframework.transaction.jta.JtaTransactionManager.doCommit(JtaTransactionManager.java:1031)
at org.springframework.transaction.support.AbstractPlatformTransactionManager.processCommit(AbstractPlatformTransactionManager.java:709)
at org.springframework.transaction.support.AbstractPlatformTransactionManager.commit(AbstractPlatformTransactionManager.java:678)
at org.springframework.test.context.transaction.TransactionalTestExecutionListener$TransactionContext.endTransaction(TransactionalTestExecutionListener.java:504)
at org.springframework.test.context.transaction.TransactionalTestExecutionListener.endTransaction(TransactionalTestExecutionListener.java:277)
at org.springframework.test.context.transaction.TransactionalTestExecutionListener.afterTestMethod(TransactionalTestExecutionListener.java:170)
at org.springframework.test.context.TestContextManager.afterTestMethod(TestContextManager.java:344)
at org.springframework.test.context.junit4.SpringMethodRoadie.runAfters(SpringMethodRoadie.java:307)
at org.springframework.test.context.junit4.SpringMethodRoadie$RunBeforesThenTestThenAfters.run(SpringMethodRoadie.java:338)
at org.springframework.test.context.junit4.SpringMethodRoadie.runWithRepetitions(SpringMethodRoadie.java:217)
at org.springframework.test.context.junit4.SpringMethodRoadie.runTest(SpringMethodRoadie.java:197)
at org.springframework.test.context.junit4.SpringMethodRoadie.run(SpringMethodRoadie.java:143)
at org.springframework.test.context.junit4.SpringJUnit4ClassRunner.invokeTestMethod(SpringJUnit4ClassRunner.java:142)
at org.junit.internal.runners.JUnit4ClassRunner.runMethods(JUnit4ClassRunner.java:51)
at org.junit.internal.runners.JUnit4ClassRunner$1.run(JUnit4ClassRunner.java:44)
at org.junit.internal.runners.ClassRoadie.runUnprotected(ClassRoadie.java:27)
at org.junit.internal.runners.ClassRoadie.runProtected(ClassRoadie.java:37)
at org.junit.internal.runners.JUnit4ClassRunner.run(JUnit4ClassRunner.java:42)
at org.eclipse.jdt.internal.junit4.runner.JUnit4TestReference.run(JUnit4TestReference.java:45)
at org.eclipse.jdt.internal.junit.runner.TestExecution.run(TestExecution.java:38)
at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.runTests(RemoteTestRunner.java:460)
at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.runTests(RemoteTestRunner.java:673)
at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.run(RemoteTestRunner.java:386)
at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.main(RemoteTestRunner.java:196)
Caused by: javax.transaction.RollbackException
at org.objectweb.jotm.TransactionImpl.commit(TransactionImpl.java:245)
at org.objectweb.jotm.Current.commit(Current.java:488)
at org.springframework.transaction.jta.JtaTransactionManager.doCommit(JtaTransactionManager.java:1028)
... 23 more

And I am sure this is because of that RuntimeException I am throwing in save but not able catch it or pass the test with expected clause. 我确信这是因为RuntimeException我投入了save但是无法捕获它或者通过expected子句传递测试。

anybody have any idea whats going wrong? 任何人都知道什么是错的?

Turned out that my first answer was wrong. 原来我的第一个答案是错的。 Both @Test(expected=...) and @ExpectedException work, but there is some incompability between the Spring TestContext and Junit 4.5 . @Test(expected = ...)和@ExpectedException都有效,但Spring TestContext和Junit 4.5之间存在一些不兼容的问题。 Using Junit 4.4 solved the problem for me. 使用Junit 4.4解决了我的问题。 Finally. 最后。

Here's a work-around I found to with Junit 4.5 - separate the @Transactional and @ExpectedException into nested functions. 这是我在Junit 4.5中找到的解决方法 - 将@Transactional和@ExpectedException分离为嵌套函数。 I guess the problem is something to do with the aop stuff spring puts around a @Transactional method. 我猜这个问题与aop的东西有关,Spring围绕一个@Transactional方法。

@Test
@ExpectedException(org.springframework.dao.DataIntegrityViolationException.class)
public void Test10UniqueName()
{
    DoTest10UniqueName();
}

@Transactional
public void DoTest10UniqueName()
{
    final String NAME = "NAME";
    ProductCategoryDAO dao = DAOFactory.getProductCategoryDAO();
    ProductCategory test1 = new ProductCategory();
    test1.setName(NAME);
    ProductCategory test2 = new ProductCategory();
    test2.setName(NAME);
    dao.save(test1);
    dao.save(test2);
}

Either you're running a unit test, in which case Spring TX shouldn't come in to play, or you're running some kind of integration test where you want to test what the save method does when your runtime exception is swallowed. 无论你正在运行一个单元测试,在这种情况下,春季TX不应该进来玩,或者你正在运行某种集成测试,你要测试的保存方法不会当你运行时异常吞噬。 I don't think anything is going wrong, you just need to make sure you understand what it is you are trying to test. 我认为没有任何问题,你只需要确保你明白你想要测试的是什么。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM