【发布时间】:2011-06-26 19:11:39
【问题描述】:
我的项目中已经编写了一些 JUnit 测试,用于在 setup 方法中填充数据。现在我已将 maven 添加到我的项目中,我想从 maven 执行所有测试用例,即使用 mvn test。现在的问题是每个测试类运行后我的数据库都没有清除。在每个类的测试用例运行后,我需要清除 HSQLDB。
【问题讨论】:
标签: java hibernate junit hsqldb
我的项目中已经编写了一些 JUnit 测试,用于在 setup 方法中填充数据。现在我已将 maven 添加到我的项目中,我想从 maven 执行所有测试用例,即使用 mvn test。现在的问题是每个测试类运行后我的数据库都没有清除。在每个类的测试用例运行后,我需要清除 HSQLDB。
【问题讨论】:
标签: java hibernate junit hsqldb
您可以通过删除架构来清除数据。默认模式称为 PUBLIC。如果执行下面的 SQL 语句,它将清除所有数据并删除所有表。
DROP SCHEMA 公共级联
或者,如果您需要表和模式对象定义,您可以创建一个文件:包含对象但不包含数据的数据库,并将以下属性添加到 .properties 文件中。使用这种类型的数据库进行测试,对数据的更改不会持久化
files_read_only=true
HSQLDB 2.2.6 及更高版本中提供的最新替代方案允许您在保留表的同时清除模式中的所有数据。在下面的示例中,PUBLIC 架构被清除。
TRUNCATE SCHEMA 公开并提交
此语句在最新版本的 HSQLDB 中得到了增强。请参阅 Truncate Statement
下的 http://hsqldb.org/doc/2.0/guide/dataaccess-chapt.html#dac_truncate_statement【讨论】:
按照 fredt 的建议,截断 SCHEMA PUBLIC RESTART IDENTITY 并提交不检查 为我工作。 DAO 的 JUnit 测试中的相关代码部分。
@After
public void tearDown() {
try {
clearDatabase();
} catch (Exception e) {
fail(e.getMessage());
}
}
public void clearDatabase() throws Exception {
DataSource ds = (DataSource) SpringApplicationContext.getBean("mydataSource");
Connection connection = null;
try {
connection = ds.getConnection();
try {
Statement stmt = connection.createStatement();
try {
stmt.execute("TRUNCATE SCHEMA PUBLIC RESTART IDENTITY AND COMMIT NO CHECK");
connection.commit();
} finally {
stmt.close();
}
} catch (SQLException e) {
connection.rollback();
throw new Exception(e);
}
} catch (SQLException e) {
throw new Exception(e);
} finally {
if (connection != null) {
connection.close();
}
}
}
根据文档在 http://hsqldb.org/doc/2.0/guide/dataaccess-chapt.html#dac_truncate_statement
如果指定了 RESTART IDENTITY,则所有表 IDENTITY 序列和所有 架构中的 SEQUENCE 对象被重置为其起始值
【讨论】:
我们在所有测试中所做的是在执行结束时回滚事务(在所有断言都通过之后)。我们使用 Spring,默认情况下测试不会在最后提交。这可确保您始终返回到数据库的初始状态(在初始创建实体表并运行 import.sql 之后)。
即使您不使用 Spring,您也可以滚动自己的 try {} finally {} 块来回滚每个测试的已启动事务。
【讨论】:
另一个解决方案列在“清除测试之间的数据库”http://www.objectpartners.com/2010/11/09/unit-testing-your-persistence-tier-code/
【讨论】:
我有一个简单的 SQL 脚本,它在每次测试之前运行,开头有以下语句:
TRUNCATE SCHEMA public AND COMMIT;
但我在测试之间遇到了锁定问题,添加它对我来说就像一个魅力:
@After
public void after() throws Exception {
if (entityManager.getTransaction().isActive()) {
entityManager.getTransaction().rollback();
}
}
【讨论】:
entityManager 来自哪里?