2012-01-17 56 views
1

我有大约10个JUnit会自动执行。我想重新设置每个数据库。我有这样一段代码:在运行JUnit测试之前重置mysql数据库

//@Transactional 
public class TestMediaObjectService extends AbstractDataAccessTest{ 

//This method reset the database, emptying the tables 
    @Test 
    public void testCreateDataBase() throws Exception { 
     TestDatabaseCreation creation = new TestDatabaseCreation(); 
     creation.resetDatabase(); 
    } 

//This is one of the methods. 
    @Test 
    public void testStoreMediaObject() throws Exception { 
//...... 
} 

当我与我使用的方法testCreateDataBase和之后运行该测试(没有那个方法)相同的脚本手动重置数据库,自动创建的表。但是,如果我运行代码,我在上面粘贴,未创建的表,所以我得到这个错误:

Caused by: com.mysql.jdbc.exceptions.jdbc4.MySQLSyntaxErrorException: Table 'one_table' doesn't exist

我怎么能运行在测试运行的其他方法之前,在每一个方法是什么?注释@Transactional已被删除,但错误仍然存​​在。

回答

3

通常您不需要手动重置数据库,因为JUNIT会在每次测试之前为您完成此操作。使用这些注释:

@TransactionConfiguration(defaultRollback = true) 
@Transactional 
@RunWith(SpringJUnit4ClassRunner.class) 

Junit将在运行后回滚测试中完成的所有事务。所有你需要的是一个现有的空数据库。如果你使用hibernate来管理你的实体,你甚至不需要拥有这些表。

如果你想要做手工,使用@Before注释在设置方法:

@Before 
public void init() { 
    createTables(); 
} 

这将在每次测试之前运行。

如果要为一个班的所有测试设置数据库表一次,请使用@BeforeClass。但通常这不是最佳实践,因为每个测试都应独立于任何其他测试。

+0

此配置不会重置数据库。它表示测试将在数据库事务中执行,事务将不会被提交,而是回滚。一切都将发生在实体管理器缓存中或未提交数据库事务。简单的单元测试应该这样工作。更复杂的集成测试不会。 – 2012-01-17 08:22:49

+0

我明白你的观点,即使这个问题没有具体说明数据是否真的需要承诺。但是:为什么你要在单元测试中实际向数据库提交数据呢?我能想到的唯一原因是测试数据库连接或事务环境,或者如果您有分布式环境。对现有数据的集成测试不应该在单元测试中完成,我认为该测试不会是独立的。它应该自己设置所有必需的数据。 – Pete 2012-01-17 08:28:12

+0

谢谢,但数据库不会重置这些注释。我得到DuplicateObjectException。我在我的应用程序中进行了一些测试,并且我有一个针对该问题的数据库。是不是在应用程序本身使用数据库 – 2012-01-17 08:38:36

相关问题