jenkins - 任何人都可以解释 groovy 闭包的魔力/詹金斯
问题描述
我想了解基于 groovy DSL 和闭包的 Jenkins 管道的一部分代码。
我有一个詹金斯文件如下:
foo {
var1 = "foo value 1"
var2 = "foo value 2"
}
我的 Jenkins 共享库中有一个 groovy 脚本(vars 目录中的 foo.groovy):
def call(body) {
def config = [:]
body.resolveStrategy = Closure.DELEGATE_FIRST
body.delegate = config
body()
println config.var1 // display foo value 1 : for me the magic is here !!
}
我想了解 groovy / jenkins 机制,即当调用闭包时,map config 是使用变量 var1 和 var2 设置的。
我(几乎)了解闭包机制和委托方法,但是我们怎么知道配置映射到闭包的委托字段的影响允许使用我的 Jenkinsfile 中声明的变量构建映射?
我希望我的问题很清楚!:)
问候,
史蒂夫
解决方案
当一个属性在闭包中被引用,并且该引用无法在闭包中解析时,会尝试在不同的“地方”解析它
this
- 闭包的
delegate
属性,可以重新分配 - 关闭的
owner
在您的示例中,var1
和var2
是无法在闭包中解析的引用示例。
以下将闭包的委托分配给config
并确保这是用于解析未解析引用的第一个“位置”
def config = [:]
body.resolveStrategy = Closure.DELEGATE_FIRST
body.delegate = config
因此,当我们在闭包中设置属性时var1
,var2
它们是针对 解析的config
,即设置为 this 的键值对Map
。
如果您的示例更改为:
foo {
def var3 = "some value"
var1 = "foo value 1"
var2 = "foo value 2"
var3 = "some value"
}
var3
不会被解决,config
因为它可以在闭包内解决。
更新
回应您的评论(我认为):为什么将闭包的委托设置为地图会导致将键值对添加到该地图?
当var1 = "foo value 1"
不能在闭包内解决时,它会根据地图解决,因为这个
def config = [:]
body.resolveStrategy = Closure.DELEGATE_FIRST
body.delegate = config
所以这实际上意味着我们在打电话
config.var1 = "foo value 1"
这是 Groovy 的简写
config.put("var1", "foo value 1")
如果您更改代码以直接调用该方法,可能会更容易理解put
,例如
def foo = {
put('var1', "foo value 1")
}
def call(body) {
def config = [:]
body.resolveStrategy = Closure.DELEGATE_FIRST
body.delegate = config
body()
println config.var1 // display foo value 1 : for me the magic is here !!
}
call(foo)
如果您在 Groovy 控制台中运行此代码,您会看到它还会打印“foo value 1”。
如果你还在苦苦挣扎,也许这个问题会有所帮助。
推荐阅读
- node.js - Kahoot.js 请求错误:错误:套接字挂起
- python - Python - 在句号之后放置空格;不是十进制数
- git - 即使 git 状态是最新的,带有 git 的 oh-my-zsh 也不会将提示中的 git 横幅更新为绿色
- xcode - 通过简单地忽略警告来处理弃用警告
- react-native - Janus React Native:向视频室添加数据/文本支持
- python - AttributeError:类型对象“SettingsFrame”没有属性“ENABLE_CONNECT_PROTOCOL”
- machine-learning - 对 julia 中的匿名函数感到困惑
- sass - :hover 效果不适用于 ReactJs 中的自定义按钮
- node.js - 如何立即收取 50% 的付款,10 天后自动收取 50% 的付款?
- python - 如何在同一个文件中写入两个不同的数据类型?