简体   繁体   中英

Reduce the pipeline script for running multiple jobs parallel

I have below snippet for getting the matching job name then trigger all of them run parallelly.

Shared library file CommonPipelineMethods.groovy

import jenkins.instance.*
import jenkins.model.*
import hudson.model.Result
import hudson.model.*

import org.jenkinsci.plugins.workflow.support.steps.*

class PipelineMethods {

def buildSingleJob(downstreamJob) {
    return {
        result = build job: downstreamJob.fullName, propagate: false
        echo "${downstreamJob.fullName} finished: ${result.rawBuild.result}"
        }
    }

}
return new PipelineMethods();

The main Jenkinsfile script:

def commonPipelineMethods;

pipeline {
    stages {
        stage('Load Common Methods into Pipeline') {
            def JenkinsFilePath = '/config/jenkins/jobs'
            commonPipelineMethods = load "${WORKSPACE}${JenkinsFilePath}/CommonPipelineMethods.groovy"
        }
        stage('Integration Test Run') {
            steps {
                script {
                    matchingJobs = commonPipelineMethods.getIntegrationTestJobs(venture_to_test, testAgainst)
                    parallel matchingJobs.collectEntries{downstreamJob-> [downstreamJob.name, commonPipelineMethods.buildSingleJob(downstreamJob)]}
                }
            }
        }
    }
}

The script works fine but looking at from Map .... parallel step for parallel the script is a bit busy and not easy to get it. The main purpose of this is I want to reduce the pipeline script to be cleaner and easy for others to help maintain. Something simple like calling the external methods as matchingJobs = commonMethods.getIntegrationTestJobs(venture, environment) , so others can understand it right away and know what the code does in this context.

I tried several ways to improve it but seem if it put part of them into building the single job outside the pipeline itself but into the external library, for example

def buildSingleJobParallel (jobFullName) {
        String tempPipelineResult = 'SUCCESS'
        result = build job: jobFullName, propagate: false
        echo "${jobFullName} finished: ${result.rawBuild.result.toString()}"
            if (result.rawBuild.result.isWorseThan(Result.SUCCESS)) {
                tempPipelineResult = 'FAILURE'
                }
    }

then Jenkins prompted me that groovy.lang.MissingMethodException: No signature of method: PipelineMethods.build() is applicable for argument types: (java.util.LinkedHashMap) values: [[job:test_1, propagate:false]]

I can understand that build() method is from Jenkins Pipeline Build Steps Plugins, but I failed to import it and use it inside that commonMethods library (this local library I just use load () method in the very first phase of my pipeline script.

So my question is

  • Could I use Jenkins Pipeline Build Step plugins inside the external library I mentioned above?
  • If it's not possible for the first question, I wonder if there's any cleaner way to make my script simpler and cleaner?

Thanks, everybody!

not sure if it runnable and looks clearer but i just tried to put all together from question and comments


//function that returns closure to be used as one of parallel jobs
def buildSingleJobParallel(steps, mjob){ 
    return {
        def result = steps.build job: mjob.fullName, propagate: false
        steps.echo "${mjob.fullName} finished: ${steps.result.rawBuild.result}"
        if (result.rawBuild.result.isWorseThan(Result.SUCCESS)) {
            steps.currentBuild.result = 'FAILURE'
        }
    }
}



stage('Integration Test Run') {
    steps {
        script {
            //build map<jobName, Closure> and run jobs in parallel
            parallel matchingJobs.collectEntries{mjob-> [mjob.name, buildSingleJobParallel(this, mjob)]}
        }
    }
}

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM