我正在尝试使用Spock围绕Spring应用程序创建集成测试。由于它不是Spring Boot应用程序,并且@SpringBootTest
注释严重干扰了该应用程序的初始化,因此我使用的配置最少。
我特别需要在应用程序中存根返回类型为Message
的对象的服务;在实际应用中,这些对象将来自第三方供应商的库,并且无法实例化或子类化,它们的成员也没有设置器,因此,我唯一的选择是为它们创建Stub
。但是,使用当前的配置(我已经大大简化了测试,只是为了了解要点):
@ContextConfiguration([TestSetup]) // supplies actual Spring beans including some JPA repos
class LogicSpec extends Specification {
@SpringBean
RestService restService = Stub()
@Autowired
ServiceUnderTest sut
@Autowired
SomeJPARepo repository;
def 'should do some business logic'() {
given:
Message m = new Stub() {
getStatus() >> "stubbed status"
}
restService.getMessage(_ as String) >> {
m
}
when:
sut.businessMethod()
then:
// just checking for side effects that `businessMethod` causes, no mocks being matched against
assert repository.findAll().every { it.processed == true }
}
}
}
在内部,ServiceUnderTest.businessMethod()
使用的Message
对象是这样的:
restService.getMessage(sid).getStatus() // should be "stubbed status"; always evaluates to null
但是, Message
stub的每个方法始终返回null ,无论我是否已为其定义行为。 Message
对象必须从其getter返回特定的值才能使测试正常工作。我希望不必将每个Message
存根声明为自己的@SpringBean
;我最终需要扩展测试以使用几个不同的Message
存根对象。我不需要模拟或间谍,因为RestService
方法的调用次数无关紧要,我只需要它发出适当的存根以供ServiceUnderTest
咀嚼。如果这个问题不寻常,或者我错过了明显的事情,我们深表歉意。我对Spock的生命周期概念略有遗忘,并且由于增加了Spring扩展而使水域特别混乱。