Spock中where子句调用静态方法时测试发现失败问题求助
Spock框架where子句调用静态方法导致测试发现失败的解决思路
问题描述
在Spock框架中,直接在where子句使用内联数据表格编写测试用例时,测试可正常通过;但将数据表格提取到静态方法并在where子句中调用该方法后,出现测试发现失败的VerifyError错误。
正常通过的测试代码
@Unroll def "max of #a and #b gives #c"() { expect: Math.max(a, b) == c where: [a, b, c] << [ [1, 0, 1], [2, 2, 2], [4, 5, 5] ] }
调用静态方法的出错代码
@Unroll def "max of #a and #b gives #c"() { expect: Math.max(a, b) == c where: [a, b, c] << dataTable() } static def dataTable() { return [ [1, 0, 1], [2, 2, 2], [4, 5, 5] ] }
错误堆栈信息
org.junit.platform.commons.JUnitException: TestEngine with ID 'spock' failed to discover tests Caused by: org.junit.platform.commons.JUnitException: MethodSelector [className = 'specs.filters.FiltersPostSpec', methodName = 'max of #a and #b gives #c', methodParameterTypes = ''] resolution failed Caused by: java.lang.VerifyError: (class: specs/filters/FiltersPostSpec, method: $spock_feature_2_3prov0 signature: ()Ljava/lang/Object;) Illegal target of jump or branch
使用版本
<groovy.version>3.0.9</groovy.version> <spock-core.version>2.1-groovy-3.0</spock-core.version> <spock-reports.version>2.3.0-groovy-3.0</spock-reports.version>
解决思路
- 升级Groovy版本:Groovy 3.0.9存在已知的字节码生成bug,导致Spock动态生成测试代码时出现
VerifyError。建议升级到Groovy 3.0.17或更高版本,该版本修复了多个字节码相关问题。 - 明确静态方法返回类型:将静态方法的返回类型从
def改为具体的List<List<Integer>>,避免Groovy动态类型带来的字节码生成歧义:static List<List<Integer>> dataTable() { return [ [1, 0, 1], [2, 2, 2], [4, 5, 5] ] } - 升级Spock版本:尝试将Spock Core升级到2.3-groovy-3.0版本,该版本对Groovy 3.x的兼容性更好,修复了多个测试发现阶段的问题。
- 替代方案:如果上述方法无效,可以改用
@Shared变量存储数据表格,在setup()方法中初始化,再在where子句中引用:@Shared List<List<Integer>> testData def setup() { testData = [ [1, 0, 1], [2, 2, 2], [4, 5, 5] ] } @Unroll def "max of #a and #b gives #c"() { expect: Math.max(a, b) == c where: [a, b, c] << testData }
内容的提问来源于stack exchange,提问作者amadain
相关产品推荐
相关产品推荐

