Deploying Java Applications to Openshift via Bamboo

Implementing a CICD process in Bamboo to deploy Java applications to Openshift can be tricky. Specially if the process needs to deploy to different stages and environments. Furthermore, you want to have control when something is deployed to production and not entrust this responsibility to master-branch merging activities. So unfortunately in this scenario using „mvn clean fabric8:resource fabric8:deploy“ is not enough.

In order to fulfil our requirements, we will to define two different phases. Phase one is when the code is committed or merged  into the master branch. Phase two is when we  deploy it to a production environment.

Phase one: Branch Updated

Bamboo provides triggers that execute predefined tasks when a branch is updated. Here we are just going to build the project source code, execute the respective tests and archive the resulting artifacts. Our plan will look like this:

Maven Task

Apart from the usual suspects, “Source Code Checkout” and “Maven POM Value Extractor”, we define additional Openshift and Maven tasks. First, we have to login to the target Openshift environment. Second we will change to the respective project (namespace). Even though we are not going to deploy anything yet, the fabric8 maven plugging needs a connection to Openshift to register the image, the imagestream and the build.

// Login into openshift
oc login --token=${bamboo.openshiftPasswordToken} --server=${bamboo.openshift4URL} --insecure-skip-tls-verify
// Choosing the project
oc project ${bamboo.openshiftProject}

After that we are going to execute “Pause Rollout”.  We do this because we want to avoid triggering a new deployment when the image is changed.

// Pause Rollout
oc rollout pause dc ${bamboo.maven.artifactId}

Next, we are going to execute fabric8 to create the deployment artifacts.

// Maven fabric8 tasks
clean install fabric8:resource fabric8:build

Last but not least, we need to archive the artifacts for phase two.archive artifacts

The docker-build.tar is actually the docker image which we are going to deploy. The “openshift.yml” file contains, among others, the following Openshift component definition: deployment configuration, route and service. The is our Springboot  properties file and we are using to automatically create a configmap. This is optional and you can use this mechanism to configure other elements.

Phase two: Deployment

The deployment can be executed at any point in time. But only after the code was build (phase one). Our Bamboo deployment plan is going to use ‚oc‘ commands for this.

Deployment tasksWe start by downloading the archived components:

Artifact download

Once completed, we log into Openshift and choose the respective project. Only then we can apply our artifacts. The first one is the which we  use to create the respective configmap.

// Create configmap
oc create configmap ${bamboo.maven.artifactId} --from-file=${bamboo.openshiftArtifacts}/${bamboo.maven.artifactId}/ --dry-run -o yaml | oc replace --force -f -

Subsequently, we are going to use the openshift.yml to create all the openshift components. Our script will first check if the components are already defined in our environment. If so we will use “oc apply”to update them. Otherwise we will use  “oc create” to create them for the first time.

#Remove whitespaces
if [[ "$OUTPUT"  =~ .*NAMEREVISION.* ]]; then
  oc apply -f $SCRIPTLOCATION/openshift.yml
  oc create -f $SCRIPTLOCATION/openshift.yml

*$DEPLOYMENT, $SCRIPTLOCATION are environment variables defined in the Bamboo task.

Next we are going to start the build using the docker-build.tar to start the build:

oc start-build ${bamboo.maven.artifactId}-s2i --from-archive=${bamboo.openshiftArtifacts}/${bamboo.maven.artifactId}/docker-build.tar

Before resuming the application rollout (remember that we paused it above?) we are going to define the autoscale. This is only required if you need more than one pod:

oc autoscale dc/$DEPLOYMENT --min 2 --max 2

*$DEPLOYMENT is an environment variables defined in the Bamboo task.

And then, we can finally start the rollout and let Openshift do the magic:

oc rollout resume dc $DEPLOYMENT

*$DEPLOYMENT is an environment variables defined in the Bamboo task.

The final steps depends more on the kind of the project. For example we define an additional route for the project and  change  the timeouts:

//Defining route
oc create route edge myproject-service-public --service=myproject-service --insecure-policy=Allow
//Changing timeouts
oc annotate route myproject-service-public --overwrite


In this post we provide a different approach on how to deploy Java to Openshift. The fabric8 tools are very good, indeed.  Unfortunately we couldn’t implement our requirements using only the provided Maven tasks. By splitting the deployment activities in two phases and combining the fabric8 generated artifacts with oc commands, we were able to implement a robust CI/CD pipeline that fulfilled our needs.