6

我正在做一个单元测试,它通过 DAO 将信息提交到 Oracle 数据库,然后检索它并检查一切都没有改变。

测试类中还有其他单元测试,在类的顶部我有:

@TransactionConfiguration (defaultRollback = true)

我想知道如何删除@NotTransactional。我没有在类上指定 Transactional,所以默认情况下没有测试应该是这样的。由于这是它自己的测试,我不知道@BeforeTransaction(或After)注释是否正确。

最大的问题是没有@NotTransactional,看起来好像unsubscribe() 函数没有运行。(垃圾标志没有改变。)

再次运行测试,在存在@rollback=false 和@NonTransactional 的情况下,我看到测试完成后数据库中的垃圾标志正确设置为true。

@RunWith (SpringJUnit4ClassRunner.class)
@TransactionConfiguration (defaultRollback = true)
public class DatabaseTest {

    @Autowired (required = true)
    private FooDao<Foo> fooDao;

    @Autowired (required = true)
    private FooService fooService;

    // other tests here that are marked @Transactional.

    @Test
    @NotTransactional
    public void testDelete() {
        Foo foo = new foo();
        foo.setTrashFlag(false);
        foo.setId(123);

        fooDao.create(foo);

        Foo fooFromDb = fooService.getFromDbById(123);
        assertNotNull(fooFromDb);

        fooService.unsubscribe(123);   // among other things, 
                                       // **sets trash flag to true.**

     // sqlSession.flushStatements();  // doesn't seem to commit the unsubscribe action


        // getFromDbById() returns ONLY Foos with trash set to false, so we expect
        // nothing returned here as we've just set trash to true, using unsubscribe().

        Foo trashedFoo = fooService.getFromDbById(123);   
        assertNull(trashedFoo);

谢谢!

4

2 回答 2

10

我不知道这是否真的是主题,但我将@NotTransactional 用于具有事务基类的方法。Spring 说要将测试分为事务性和非事务性测试,但我发现在我的情况下,只需将以下内容添加到方法中,就可以禁用事务并让我删除不推荐使用的注释:

@Transactional(propagation = Propagation.NEVER)

我以为我只是把它放在这里给那些和我做同样事情的人。

于 2013-09-03T11:01:07.443 回答
6

@Rollback(false)并不总是足够的,它只意味着事务不会在测试结束时回滚。但它仍然在一个事务中运行测试,这有时会导致与其他正在运行的事务发生冲突。

正如 Spring 建议的那样,您有两种选择:

  1. 将测试类一分为二,事务性测试可以是带有注释的测试类中的@Transactional,而非事务性测试可以是没有事务性注释的测试类中的。
  2. 使用方法注释而不是类注释,用 注释每个事务测试@Transactional,但将其从类范围中删除

引用 Spring文档

从 Spring 3.0 开始,@NotTransactional不赞成将非事务性测试方法移动到单独的(非事务性)测试类或@BeforeTransactionor@AfterTransaction方法。作为用 注释整个类的替代方法,可以考虑用;@Transactional注释单个方法。@Transactional这样做允许在同一个测试类中混合使用事务和非事务方法,而无需使用@NotTransactional.

于 2013-03-21T09:27:05.477 回答