Groovy 每个实例的元类方法重写在 Spock 测试中没有按预期工作
Groovy per instance metaClass method override doesn't work as expected in Spock test
我有一个 class 方法叫做 execute()。在一些 Spock 单元测试中,我模拟了 execute 方法并给它一个像这样的模拟闭包:
def setup () {
rule = new DynamicRule ()
}
def "test default execution " (){
given : "basic AORule "
def mockres
rule.metaClass.execute = {-> mockres = "did nothing"} //mock the action
def res = rule.execute()
expect : "execute should do nothing "
mockres == "did nothing"
}
如果我 运行 这个测试失败了。在 idea 编辑器中,模拟闭包显示为带下划线的,但下一行的 rule.execute() 不是 - 所以它可以看到方法。
如果我为此更改此测试:
rule.metaClass.execute2 = {-> mockres = "did nothing"} //mock the action
def res = rule.execute2()
然后测试通过。
在 Spock 之外,我只是 运行 一个简单的 Groovy 脚本,并做了方法重载,并且正如我所期望的那样正常工作,并且该方法是用闭包模拟的
class A {
def execute () {
println "thing"
}
}
def c = new A()
def res
c.execute()
c.metaClass.execute = {-> res =2 ; println "modified thing "; }
c.execute ()
println "res = "+ res
为什么 Spock 测试中没有出现同样的情况?
单元存根如何为 Spock 正确测试闭包?
此修改版本测试成功:
def "test default execution " (){
given : "basic AORule "
def mockres
def stub = new StubFor(AORule)
stub.demand.execute { mockres = "did nothing" }
// rule.metaClass.execute = {-> mockres = "did nothing"} //mock the action
// def res = rule.execute()
expect : "execute should do nothing "
stub.use {
rule.execute()
mockres == "did nothing"
}
}
为什么简单的 per metaclass 在 Spock 中不起作用?
这是 Groovy >= 2.4.3 上的未决问题,此处:GROOVY-7368。
用元类覆盖私有方法时存在错误。
我有一个 class 方法叫做 execute()。在一些 Spock 单元测试中,我模拟了 execute 方法并给它一个像这样的模拟闭包:
def setup () {
rule = new DynamicRule ()
}
def "test default execution " (){
given : "basic AORule "
def mockres
rule.metaClass.execute = {-> mockres = "did nothing"} //mock the action
def res = rule.execute()
expect : "execute should do nothing "
mockres == "did nothing"
}
如果我 运行 这个测试失败了。在 idea 编辑器中,模拟闭包显示为带下划线的,但下一行的 rule.execute() 不是 - 所以它可以看到方法。
如果我为此更改此测试:
rule.metaClass.execute2 = {-> mockres = "did nothing"} //mock the action
def res = rule.execute2()
然后测试通过。
在 Spock 之外,我只是 运行 一个简单的 Groovy 脚本,并做了方法重载,并且正如我所期望的那样正常工作,并且该方法是用闭包模拟的
class A {
def execute () {
println "thing"
}
}
def c = new A()
def res
c.execute()
c.metaClass.execute = {-> res =2 ; println "modified thing "; }
c.execute ()
println "res = "+ res
为什么 Spock 测试中没有出现同样的情况?
单元存根如何为 Spock 正确测试闭包?
此修改版本测试成功:
def "test default execution " (){
given : "basic AORule "
def mockres
def stub = new StubFor(AORule)
stub.demand.execute { mockres = "did nothing" }
// rule.metaClass.execute = {-> mockres = "did nothing"} //mock the action
// def res = rule.execute()
expect : "execute should do nothing "
stub.use {
rule.execute()
mockres == "did nothing"
}
}
为什么简单的 per metaclass 在 Spock 中不起作用?
这是 Groovy >= 2.4.3 上的未决问题,此处:GROOVY-7368。
用元类覆盖私有方法时存在错误。