基于JPA的JUnit测试最佳实践

mla*_*tti 30 java junit testng maven-2 jpa

这是一个奇怪的问题,但它已经困扰了我几个月了.我使用Wicket + Hibernate构建了一个基于JPA的Web应用程序(使用Maven构建),并希望直接测试DAO层.我创建了一个特定的src/test/resources/META-INF/persistence.xml文件,用于测试,但是已经遇到与WTP等冲突.为了解决这些问题,我创建了一个单独的测试项目,其中单元测试是实时的.有没有更好的方法来管理JPA项目的单元测试而不在持久性文件之间进行决斗?

附录:其他测试框架(例如TestNG)是否会使这更容易?

Aar*_*lla 16

你可能想试试mockito.测试的工作方式如下:

你使用mockito来"实现" EntityManager.您可以使用mockito的方法来代替实际代码,"如果应用程序调用getReference(),则返回此对象".在后台,mockito将创建一个代理实例,该实例拦截Java方法调用并返回您指定的值.对其他方法的调用将返回null.

createQuery()模拟类似的方式工作但你首先需要创建一个模型Query然后使用相同的方法getReference()(返回查询模型).

由于您不使用真正的EM,因此您不需要真实的EM persistence.xml.

一个更简单的解决方案是,如果您可以设置一些属性来更改persistence.xml文件的名称,但我不认为这是可能的.

其他一些可能有用的链接:

  • 在这种情况下,第一个链接中有一个解决方案:您可以在persistence.xml中指定多个"持久性单元",并在单元测试中选择另一个. (2认同)

top*_*hef 5

我们使用双persistence.xml文件来生成和测试运行时,但它只是一个类路径相关的问题(我们使用Eclipse但不依赖于WTP插件).两者之间的唯一区别是生产版本不包含实体定义.

我们不使用模拟框架来测试JPA,因为这不会为我们的测试添加任何值.测试确实使用与PostgreSQL数据库对话的JPA进行实际数据访问.

我们的测试方法基于持久层的Spring测试框架:事务内测试.我们的应用程序是基于Spring的,但是这种方法同样适用于想要利用Spring测试类的任意应用程序.实质是每个测试都在一个永不提交的事务中运行,最后(在tearDown中)它会自动回滚.这以非常好的不引人注目和透明的方式解决了数据污染和测试依赖的问题.

Spring测试框架可灵活地允许多事务测试,但这些特殊情况构成的测试不超过10%.

我们仍然使用JUnit 3.8的遗留支持,但JUnit 4的新Spring TestContext框架看起来非常有吸引力.

为了设置事务内测试数据,我们使用构建业务实体的内部实用程序类.由于它是在所有测试之间共享的,因此通过使用标准和可靠的方法来设置测试数据,维护和支持它的开销非常大.

Spring DI有助于使测试简洁和自我描述,但它不是一个关键特性.