Jenkins 从管道脚本方法获取控制台记录器(或TaskListener)

Jenkins 从管道脚本方法获取控制台记录器(或TaskListener),jenkins,jenkins-pipeline,jenkins-groovy,Jenkins,Jenkins Pipeline,Jenkins Groovy,如果在管道脚本(Jenkinsfile)、全局管道库的vars/或src/类中有管道脚本方法,那么如何获取控制台日志的OutputStream?我想直接写入控制台日志 我知道我可以echo或println,但为此,我需要在不产生额外输出的情况下编写。我还需要能够将OutputStream传递给其他对象 我知道我可以调用tasklister.getLogger(),如果我可以得到tasklister(实际上是hudson.util.streamtasklister)实例,但是如何调用呢 我试过:

如果在管道脚本(
Jenkinsfile
)、全局管道库的
vars/
src/
类中有管道脚本方法,那么如何获取控制台日志的
OutputStream
?我想直接写入控制台日志


我知道我可以
echo
println
,但为此,我需要在不产生额外输出的情况下编写。我还需要能够将
OutputStream
传递给其他对象

我知道我可以调用
tasklister.getLogger()
,如果我可以得到
tasklister
(实际上是
hudson.util.streamtasklister
)实例,但是如何调用呢

我试过:

  • 我研究了
    manager.listener.logger
    (来自groovy postbuild插件),在早期构建上下文中,我从中调用它不会生成写入作业控制台日志的输出流

    echo "listener is a ${manager.listener} - ${manager.listener.getClass().getName()} from ${manager} and has a ${manager.listener.logger} of class ${manager.listener.logger.getClass().getName()}"
    
    印刷品

    listener is a hudson.util.LogTaskListener@420c55c4 - hudson.util.LogTaskListener from org.jvnet.hudson.plugins.groovypostbuild.GroovyPostbuildRecorder$BadgeManager@58ac0c55 and has a java.io.PrintStream@715b9f99 of class java.io.PrintStream
    
  • 我知道您可以通过
    context.get(tasklister.class)
    StepContext
    获取它,但我不在
    步骤中,我在
    CpsScript
    (即
    WorkflowScript
    Jenkinsfile

  • 从注册为
    steps
    script属性的
    DSL
    实例获得的
    CpsFlowExecution
    中查找它,但我无法确定如何发现创建时传递给它的
    TaskListener
怎么这么难?我错过了什么?有这么多的间接魔法,我发现它难以置信地难以导航系统


顺便说一句,我知道直接访问被脚本安全性阻止了,但我可以创建
@Whitelisted
方法,而且全局库的
vars/
中的任何内容都始终是白名单的。

在我的头撞了几天这个问题之后,我想我有了一个解决方案:

CpsThreadGroup.current().execution.owner.listener

它很难看,我不知道它是否正确,或者是否有更好的方法,但似乎有效。

您可以从Jenkins根对象访问构建对象:

def listener = Jenkins.get()
    .getItemByFullName(env.JOB_NAME)
    .getBuildByNumber(Integer.parseInt(env.BUILD_NUMBER))
    .getListener()

def logger = listener.getLogger() as PrintStream

logger.println("Listener: ${listener} Logger: ${logger}")
结果:

Listener: CloseableTaskListener[org.jenkinsci.plugins.workflow.log.BufferedBuildListener@6e9e6a16 / org.jenkinsci.plugins.workflow.log.BufferedBuildListener@6e9e6a16] Logger: java.io.PrintStream@423efc01

这比我想出的任何黑客都好,所以非常感谢你的提示。很高兴我不是唯一一个对这个问题感到非常沮丧的人。我最终放弃了构建控制台过滤器的努力,该过滤器通过
withContext
将任意范围的控制台输出分组到HTM5
……
块中:很明显,我必须在扩展中编写自己的ConsoleAnnotation子类和包,构建它,等等,我可以将它作为@Extension绑定到全局库中,因为读取控制台的代码看不到这一点。这太难了。如果我有时间,我想回去,因为当前基于regexp的控制台折叠插件对控制台日志大小的影响非常可怕,不便于管道使用。我偶然发现了另一个解决方案(未经测试),它似乎将
StepContext.get()
暴露到管道脚本中:那个小小的项目符号“context” .... 啊。这看起来很有希望,我会调查的。詹金斯2.190.1。我得到“没有这样的属性:类:groovy.lang.Binding的CpsThreadGroup”。我应该升级一些插件吗?@Mzzl的上述解决方案对我有效。“我还需要能够将OutputStream传递给其他东西。”。。如果你能做到这一点,请解释一下如何做到。