In the previous article of this example series, we created a stateless Jenkins docker container that can be initialized solely by scripts. In that example, a seed job for the jobDsl plugin was also implemented. This job was later on used to create an automated simple Jenkins job,-inline-. Now we are ready to shape our Stateless Jenkins container to meet more advanced requirements, – advanced jobs as code-.
We will extend previous seedJob implementation further to create more complex jobs programmatically. Our extended seedJob will poll a job definition repository, and it will gather the information on how to create new jobs for some other remote repositories.
Summary of the steps:
- Extend
jenkins/init.groovy/1-init-dsl-seed-job.groovy
script to enable polling of remote repositories so that it can check these repositories for new job descriptions. - Automate the installation of the tools, which will be needed by the builds (e.g. maven, JDK, etc.)
- Implement some job description scripts in the repository (folder), which will be polled by the seed job initialization script.
- Add Jenkinsfile(s) to the target projects which are referenced in the job definition script(s).
- Run and test the example.
1. Extend jobDsl script
The jobDsl script 1-init-dsl-seed.job.groovy
in the previous example is implemented to create a simple “Hello world” job. We passed a DSL job script to the seed job’s “scriptText” attribute to achieve this.
Implement “Job Configuration Repository” configuration
As we stated earlier, we are going to extend this script to define more advanced jobs via groovy scripts. The extended seed job will poll a remote repository, then it will scan the contents for groovy based job descriptions. To achieve this goal, we need to define an SCM and pass this to the freestyle job (the seed job):
In addition to SCM definition, we also defined where and how to find the job definition scripts in that SCM,-“jobScriptFile“-. The snippet below shows how the “jobScriptFile” variable is used: It defines a jobDsl executor ( ExecuteDslScripts
)instance and passes jobScriptFile
variable to the ‘targets
‘ attribute of this instance:
The final form of the seed job script and summary of the tasks
In order to save some space, I will not show the full script here. You can reach the final version from the example “CI as Code” repository.
Let’s summarize what this script is doing for our “Jenkins Jobs as Code” goal:
- It will poll the master branch of the repository ‘https://github.com/entrofi/oyunbahcesi.git‘
- Check for groovy scripts under the folder
ci_cd/jenkins/configs/jobdsl/
- Execute found groovy scripts to create new Jenkins jobs. The scripts in this remote repository can poll any number of repositories and can define different types of Jenkins jobs or views.
2. Installing Tools
Every build-job has it’s own tooling requirements and in order to keep our “stateless CI/CD” goal, we should be able to automate such kind of tool installations. The example projects that we are going to define in the next section are java projects with maven build support. Let’s showcase how to install these tools via Jenkins initialization scripts:
The “2-install-tools.groovy” script installs two different versions of JDK and maven for us.
Java Installation
Maven Installation
The final form tool installation script can be found here
3. Implementing Job Descriptions
In this section, we are going to implement some example job descriptions in the remote repository. Go to jenkins/configs/jobdsl
folder, and add a groovy script file called createJobs.groovy
:
This groovy script uses jobDsl API to create multibranch jobs for the remote repositories which are defined in the multipbranchJobs array. The factory
section of the implementation checks if the remote repositories have Jenkinsfile
s, and creates the pipelines for each accordingly.
This snippet demonstrates how to create a multi-branch job using jobDsl API; however, we are not limited in terms of the variety of job descriptions. We can define any kind of Jenkins jobs, including build monitors, list views, free-style jobs, simple pipeline jobs, etc., using this API.
4. Adding Jenkinsfile to the target projects
The rest is easy; in section three we defined a target project, – “entrofi/spring/restassured-asciidoctor” -, in “multiBranchJobs” array. To create her own jobs, one can define further projects in a similar way, and add a Jenkinsfile to the target project. After completing this, it’s just a matter of running the stateless Jenkins Docker image.