首页 > 解决方案 > 无法使用 Jenkins 在远程主机的后台并行运行多个命令

问题描述

我有一个 jenkins 作业 DSL,它使用“限制该项目可以在哪里运行”标签在远程节点(Linux 操作系统)上运行。

它有“构建”步骤->“执行外壳”

在我提到的执行外壳中

sh /app/runalljobs.sh &

在远程节点主机上,runalljobs.sh 如下所示:

cat runalljobs.sh

ansible-playbook /app/test.yml -e argu=arg1
ansible-playbook /app/test.yml -e argu=arg2
.....
.....
ansible-playbook /app/test.yml -e argu=arg16

runalljobs.sh 假设在 runalljob.sh 执行时会在后台启动 16 个 ansible 进程。

当从远程节点 putty shell 手动执行脚本时,这可以正常工作。

但是,我希望脚本在使用未发生的 jenkins 作业调用时启动 ansible 进程以在远程节点的后台运行。

我也试过评论sh /app/runalljobs.sh &

并在“执行外壳”中添加单独的 ansible 命令,如下所示:

ansible-playbook /app/test.yml -e argu=arg1 &
ansible-playbook /app/test.yml -e argu=arg2 &
.....
.....
ansible-playbook /app/test.yml -e argu=arg16 &

但这也没有触发目标节点上的 ansible 进程。

如果我删除“&”然后所有ansible命令在远程上一个接一个地连续运行,它就可以工作。

但是,我希望在后台并行触发所有 ansible 命令,并且 Jenkins 执行程序应该继续执行其他执行 shell 任务。

你能建议我如何达到要求吗?

标签: jenkinsparallel-processingbackgroundansiblejenkins-job-dsl

解决方案


Jenkins 允许您并行执行任务,但有一个问题。这需要您切换到Jenkins Pipeline,然后使用parallel. 然后,您的构建脚本将如下所示:

pipeline {
    agent 'my-remote-machine'
    stages {
        ...
        stage('Ansible stuff') {
            parallel {
                stage('arg1') {
                    steps {
                        sh 'ansible-playbook /app/test.yml -e argu=arg1'
                    }
                }
                stage('arg2') {
                    steps {
                        sh 'ansible-playbook /app/test.yml -e argu=arg2'
                    }
                }
                ...
            }
        }
    }
}

如果您的命令行非常相似(如在您的示例中),您可以使用matrix部分来简化代码:

matrix {
    axes {
        axis {
            name 'ARG'
            values 'arg1', 'arg2', 'arg3'
        }
    }
    stages {
        stage('test') {
            sh 'ansible-playbook /app/test.yml -e argu=${ARG}'
        }
    }
}

我知道这个解决方案是一个彻底的改变——Jenkins Pipelines 是一个全新的 CI 世界。但这可能是值得的,因为 Jenkins 的作者非常提倡管道,并且许多插件都被重写以与它们一起使用。


推荐阅读