如何避免在 Spock 中强制转换参数

How to avoid casting arguments in Spock

我想从存储库中获取一个列表并断言其内容。

在下面的代码中,我收到一条警告,指出 Object 无法分配给 List

有没有办法添加更好的参数来处理这种情况?

myDomainObjectRepository.save(_) >> { arguments ->
   final List<MyDomainObject> myDomainObjects = arguments[0]
   assert myDomainObjects == [new MyDomainObject(someId, someData)]
}

docs似乎是准确的:

如果闭包声明了一个无类型参数,它会被传递给方法的参数列表

不过,我刚刚更改了使用 rightShift + arguments 接受单一类型参数的规范,它确实有效。试试吧。

详细说明 Opals 答案:docs 中有两个部分和一个脚注与此处相关:

If the closure declares a single untyped parameter, it gets passed the method’s argument list:

In most cases it would be more convenient to have direct access to the method’s arguments. If the closure declares more than one parameter or a single typed parameter, method arguments will be mapped one-by-one to closure parameters[footnote]:

脚注:

The destructuring semantics for closure arguments come straight from Groovy.

问题是您只有一个参数列表,并且由于删除了泛型 groovy 无法确定您是否真的想要展开列表。

所以一个非List参数就可以正常工作:

myDomainObjectRepository.save(_) >> { MyDomainObject myDomainObject ->
   assert myDomainObject == new MyDomainObject(someId, someData)
}

List 参数与第二个参数组合,例如 save(List domain, boolean flush)

myDomainObjectRepository.save(_, _) >> { List<MyDomainObject> myDomainObjects, boolean flush -> 
   assert myDomainObjects == [new MyDomainObject(someId, someData)]
}

所以文档对这种边缘情况有点误导。恐怕你在这个案例中被困住了。


编辑:如果您这样做,您应该能够摆脱 IDE 警告。

myDomainObjectRepository.save(_) >> { List<List<MyDomainObject>> arguments ->
   List<MyDomainObject> myDomainObjects = arguments[0]
   assert myDomainObjects == [new MyDomainObject(someId, someData)]
}