Groovy:在 shouldFail() 内部时失去 $it 的作用域

Groovy: Losing scope on $it when inside of shouldFail()

我有这个 groovy 代码,它在实例化一个新的 Build 对象时检查软件版本字符串的格式是否正确。我有一个要测试的无效构建字符串列表。下面是我的测试代码。我相信这个测试失败了,因为我在 shouldFail 中丢失了 "it" 的范围。我相信这是真的,因为如果我从 shouldFail.

内部打印它,"it" 的值始终为 null
void testInValidBuildStrings() {

      ['4.0..','10.0','11.0. 0.1234-8','9.-.1.1.1','9.foo.0.1'].each {
              shouldFail { 
                    println it //always null
                    Build test = new Build("productName", it, "123456")};         
              }
 }

下面案例的第二个版本有效(我假设),因为我首先将 "it" 分配给名为 build 的变量。我认为它的范围一定在 shouldFail() 内部发生了变化,但我不确定是否发生了这种情况。

void testInValidBuildStrings() {

      ['4.0..','10.0','11.0. 0.1234-8','9.-.1.1.1','9.foo.0.1'].each {
              def build = it;
              shouldFail { Build test = new Build("productName", build, "123456")};         
      }
 }

在尝试迭代 shouldFail() 时,是否有比我在下面所做的更优雅/更正确的解决方案?说实话,定义构建的额外行让我很烦:)

是的,是的。只需命名闭包的参数:

void testInValidBuildStrings() {

      ['4.0..','10.0','11.0. 0.1234-8','9.-.1.1.1','9.foo.0.1'].each { el ->
              shouldFail { 
                    println el 
                    Build test = new Build("productName", el, "123456")};         
              }
 }

shouldFail 有自己的 it - 因此你需要区分它们。

基本上,这里有 2 个嵌套闭包。每个闭包都定义了默认变量 'it' 。在 shouldFail 闭包中,它的那个实例没有价值。您可以通过命名第一个闭包中的变量并在第二个闭包中使用它而不是 'it' 来解决此问题。

closure {varName->
  secondClosure {
   println "$varName is not equal to $it"
  }
}

您将以下内容显示为工作代码:

void testInValidBuildStrings() {

    ['4.0..','10.0','11.0. 0.1234-8','9.-.1.1.1','9.foo.0.1'].each {
        def build = it;
        shouldFail { 
            Build test = new Build("productName", build, "123456")         
        }
    }
}

我会把它简化成这样:

void testInValidBuildStrings() {

    ['4.0..','10.0','11.0. 0.1234-8','9.-.1.1.1','9.foo.0.1'].each { build ->
        shouldFail { 
            new Build("productName", build, "123456")      
        }
    }
}