为什么不使用Grails3.2为单元测试注入sessionFactory?
我遇到了一个问题,扩展HibernateSpect的单元测试失败了,因为为什么不使用Grails3.2为单元测试注入sessionFactory?,grails,gorm,spock,Grails,Gorm,Spock,我遇到了一个问题,扩展HibernateSpect的单元测试失败了,因为sessionFactory没有被注入到被测服务中。每当在测试期间调用会话工厂上的方法时,我都会得到一个NullPointerException(例如java.lang.NullPointerException:无法调用null对象上的方法getClassMetadata()),测试随后失败 我正在使用Grails3.2.4和Hibernate5 当测试使用@TestMixin(HibernateTestMixin)时,这是
sessionFactory
没有被注入到被测服务中。每当在测试期间调用会话工厂
上的方法时,我都会得到一个NullPointerException
(例如java.lang.NullPointerException:无法调用null对象
上的方法getClassMetadata()),测试随后失败
我正在使用Grails3.2.4和Hibernate5
当测试使用@TestMixin(HibernateTestMixin)
时,这是有效的,但在一些更新中,mixin似乎已被弃用,建议改用HibernateSpect
以下是我的测试中的一个片段:
class TestDatabaseServiceSpec extends HibernateSpec {
def setup() {
}
def cleanup() {
}
void "test method"() {
when:
service.method()
then:
true
}
}
下面是测试中服务的一个片段:
void method() {
...
TABLE_NAMES.add(sessionFactory.getClassMetadata('MyDomain').tableName)
...
}
我已尝试在setup
方法中设置service.sessionFactory
,以及使用测试中可用的sessionFactory
设置setupSpec
方法,但不幸的是,这没有起到任何作用。我曾考虑过使用集成测试,但我真的很想看看是否可以像以前一样继续进行这个单元测试。是否有人知道我是否做得不对,或者是否有解决方法
谢谢大家! 查看
hibernatespect
的源代码可能会给出一些提示。可能您正在使用的Hibernate 5 grails插件中没有getSessionFactory()
方法
我在Grails3.2.5中使用org.grails.plugins:hibernate5:6.0.6
,在单元测试中sessionFactory对我来说不是空的
我知道升级并不总是可能的,但它可以给出问题的根源
更新:
service.sessionFactory = sessionFactory
也必须在测试设置中调用。对我有效的是将注释
@FreshRuntime
添加到规范中,并将doWithSpring
闭包添加到为我设置sessionFactory
的测试中(即sessionFactory(InstanceFactoryBean,sessionFactory,sessionFactory))。另外,我确保将service.sessionFactory=sessionFactory
和service.transactionManager=transactionManager
添加到setupSpec
方法中。最后,我需要重写getDomainClasses()
,以处理我想在测试中使用的所有域对象。谢谢你的帮助 自3.2.3以来,新性状的试验混合子已被弃用。
自Grails3.3以来,Grails测试支持框架用于所有测试
单元测试。这种支持提供了一组特性
然而,我仍然发现自己在使用HibernateSpect,因为我可以从中获得多个域类,以及服务的ServiceUnitTest。HibernateSpect具有所需的sessionFactory。
例如
所以我需要一个单元测试特性或基类,我花了几个小时试图让新特性满足我的需求。甚至我也开始对DataTest类进行子类化,试图让它为我提供sessionFactory,但最终还是使用了
HibernateSpect
,能够用几个域、服务和sessionFactory运行一个测试类真是太好了。Grails有一个明确的测试:您可以尝试添加@Entity(MyDomain)注释在您的spec类上,因为它可能触发某些东西,所以它可以工作。@bassmartin感谢您的回答。我认为@Entity(MyDomain)不起作用,因为注释上没有value属性。另外,我在没有(MyDomain)的情况下尝试了它,我看到了相同的错误。谢谢。我确实检查了hibernatespect
,看到getSessionFactory()
。我还将我的应用程序升级为使用Grails3.2.5,并使用相同版本的hibernate5插件。我还在setup
中调用了service.sessionFactory=sessionFactory
,然后在setupSpec
中调用了。因为服务被标记为事务性的,所以我还包括了service.transactionManager=transactionManager
。由于服务中的nullsessionFactory
,我仍然看到相同的NullPointerException。
class MyServiceSpec extends HibernateSpec implements ServiceUnitTest<MyService>{
List<Class> getDomainClasses() { [Tag, TagLink, TagLinkValue, TagValue, TestDomain] }
...
def setup() {
service.sessionFactory = sessionFactory
...
}
// tests here with all those domain classes available and the service
}
def statelessSession = sessionFactory.openStatelessSession()
String queryString = "select DISTINCT(t.tagRef) from com.fmr.aps.taggable.TagLink t group by t.tagRef order by t.tagRef ASC"
Query query = statelessSession.createQuery(queryString)
query.setReadOnly(true);
ScrollableResults results = query.scroll(ScrollMode.FORWARD_ONLY);