在Grails Spock规范测试中注入依赖项 [英] Inject dependencies in Grails Spock Specification test

查看:687
本文介绍了在Grails Spock规范测试中注入依赖项的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述



这些测试放置在test / integration目录中,并且从 spock.lang.Specification



我该如何实现这一目标?

注意:我看过这篇文章如何将弹簧豆注入spock测试,但它与grails无关。

编辑:

我想要的依赖项在我的 SecUser 子类中调用 springSecurityService 命名为 Player 。失败的方法是在 beforeInsert()中调用的 encodePassword()



我可以在一些测试中嘲笑这个 encodePassword()方法,但是当我想测试我的控制器方法 save(),我无法模拟正在创建的 Player ,因为它全部发生在controllers方法中。



改为扩展 IntegrationSpec 后,这是我的测试代码:

 包intertigre.test.domain 
import intertigre.domain.Fecha;
import intertigre.test.util.DomainFactoryTestService
import grails.plugin.spock.IntegrationSpec
import grails.test.mixin.TestFor

@TestFor(Fecha)
class FechaSpec extends IntegrationSpec {

DomainFactoryTestService domainFactoryTestService = new DomainFactoryTestService()
$ b $ def'test'(){
given:
def fecha = new Fecha()
when:
fecha.save()
then:
Fecha.get(1)== fecha
}


运行 grails test-app时出现此异常:spock

  java.lang.NullPointerException:无法在null对象上获取属性'mainContext'
at grails.plugin.spock.IntegrationSpec。$ spock_initializeSharedFields(IntegrationSpec.groovy)

一个当我单独运行测试时:

  |失败:intertigre.test.domain.FechaSpec 
| java.lang.NullPointerException:在grails.plugin.spock.IntegrationSpec.setupSpec(IntegrationSpec.groovy:47)上的空对象
上无法获得属性'autowireCapableBeanFactory'
|失败:intertigre.test.domain.FechaSpec
| java.lang.NullPointerException:无法调用方法isActive()对null对象
在grails.test.mixin.support.GrailsUnitTestMixin.shutdownApplicationContext(GrailsUnitTestMixin.groovy:232)
在org.spockframework.util.ReflectionUtil .invokeMethod(ReflectionUtil.java:176)
at org.spockframework.runtime.extension.builtin.JUnitFixtureMethodsExtension $ FixtureType $ FixtureMethodInterceptor.intercept(JUnitFixtureMethodsExtension.java:145)
at org.spockframework.runtime.extension .MethodInvocation.proceed(MethodInvocation.java:84)
at org.spockframework.util.ReflectionUtil.invokeMethod(ReflectionUtil.java:176)


解决方案

尝试将springSecurityService声明为测试,就像在控制器中做的那样。 Grails应该为你做所有的工作)



对于集成测试,你可以这样做:

 包intertigre.test.domain 
import intertigre.domain.Fecha;
import intertigre.test.util.DomainFactoryTestService
import grails.plugin.spock.IntegrationSpec

class DomainFactoryTestServiceSpec extends IntegrationSpec {

def domainFactoryTestService // you不需要创建一个新的实例,它是通过弹簧注入的
$ b $ def'test'(){
given:
// ...
when:
// ...
then:
// ....
}

如果你需要测试一个特定的域对象(作为你的Fecha类),你可能需要一个单元测试,如下所示:

 包intertigre.test.domain 
导入intertigre.domain.Fecha
导入intertigre.test.util.DomainFactoryTestService
导入grails.test.mixin.TestFor
import grails.test.mixin.Mock
import spock.lang.Specification

@TestFor(Fecha)
@Mock([OtherObject1,OtherObject2])
类FechaSpec扩展了规范{

def domainFactoryTestSer如果你需要服务

def'test'(){
given:
def fecha = new Fecha()
和:
def oo1 = new OtherObject1()
when:
// ...
then:
// ....
}

你也可以使用单元测试来测试服务,这取决于你要测试什么(一个类 - 服务 - 或情况 - 服务的使用方式 - )。

当然,这里的代码还没有经过测试,可以包含拼写错误。 :)但我希望你能明白我如何测试。


I need to get the dependencies injected in my domain objects in my tests.

This tests are placed in the test/integration directory and extends from spock.lang.Specification.

How can I achieve this?

Note: I've seen this post How to inject spring beans into spock test, but it is not related with grails.

Edit:

The dependency I want to get injected is springSecurityService in my SecUser subclass called Player. The method that is failing is the encodePassword(), which is called in the beforeInsert().

I can mock this encodePassword() method in some tests, but when I want to test my controllers method save(), I can't mock the Player that is being created because it all happens inside the controllers method.

After changing to extend IntegrationSpec, this is my test code:

package intertigre.test.domain
import intertigre.domain.Fecha;
import intertigre.test.util.DomainFactoryTestService
import grails.plugin.spock.IntegrationSpec
import grails.test.mixin.TestFor

    @TestFor(Fecha)
    class FechaSpec extends IntegrationSpec{

    DomainFactoryTestService domainFactoryTestService = new DomainFactoryTestService()

    def 'test'(){
        given:
            def fecha = new Fecha()
        when:
            fecha.save()
        then:
            Fecha.get(1) == fecha
    }

}

I'm getting this exception when running grails test-app :spock:

java.lang.NullPointerException: Cannot get property 'mainContext' on null object
    at grails.plugin.spock.IntegrationSpec.$spock_initializeSharedFields(IntegrationSpec.groovy)

And this one when I run the test alone:

| Failure:  intertigre.test.domain.FechaSpec
|  java.lang.NullPointerException: Cannot get property 'autowireCapableBeanFactory' on null object
    at grails.plugin.spock.IntegrationSpec.setupSpec(IntegrationSpec.groovy:47)
| Failure:  intertigre.test.domain.FechaSpec
|  java.lang.NullPointerException: Cannot invoke method isActive() on null object
    at grails.test.mixin.support.GrailsUnitTestMixin.shutdownApplicationContext(GrailsUnitTestMixin.groovy:232)
    at org.spockframework.util.ReflectionUtil.invokeMethod(ReflectionUtil.java:176)
    at org.spockframework.runtime.extension.builtin.JUnitFixtureMethodsExtension$FixtureType$FixtureMethodInterceptor.intercept(JUnitFixtureMethodsExtension.java:145)
    at org.spockframework.runtime.extension.MethodInvocation.proceed(MethodInvocation.java:84)
    at org.spockframework.util.ReflectionUtil.invokeMethod(ReflectionUtil.java:176)

解决方案

Try declaring the springSecurityService into the test, as you would do in a controller. Grails is supposed to do all the job for you :)

For an integration test you do something like this:

package intertigre.test.domain
import intertigre.domain.Fecha;
import intertigre.test.util.DomainFactoryTestService
import grails.plugin.spock.IntegrationSpec

class DomainFactoryTestServiceSpec extends IntegrationSpec{

def domainFactoryTestService // you dont need to create a new instance, it's injected by spring

def 'test'(){
     given:
         // ...
     when:
         // ...
     then:
         // ....
 }

If you need to test a specific domain object (as your Fecha class), you probably need a unit test, something like this:

package intertigre.test.domain
import intertigre.domain.Fecha
import intertigre.test.util.DomainFactoryTestService
import grails.test.mixin.TestFor
import grails.test.mixin.Mock
import spock.lang.Specification

@TestFor(Fecha)
@Mock([OtherObject1, OtherObject2])
class FechaSpec extends Specification {

def domainFactoryTestService // same thing here, if you need the service

def 'test'() {
     given:
         def fecha = new Fecha()
     and:
         def oo1 = new OtherObject1()
     when:
         // ...
     then:
         // ....
 }

You can use unit test to test services as well, it depends on what are you going to test (a class -the service- or a "situation" -the way the service is used-).

Ps. Of course, this code here hasn't been tested and can contain typos. :) But I hope you get my point about how to test.

这篇关于在Grails Spock规范测试中注入依赖项的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆