Latest posts

Lockable Resources Jenkins 2.0 pipeline builds

With Jenkins 2.0 pipeline builds you can improve the utilisation of your build servers by increasing the concurrency of the jobs. In our case, we are using Jenkins to build iOS apps with Fastlane and Android apps with Gradle. In both cases we run unit tests that involve the build server (a Mac Mini) firing up a simulator to run the tests on. Unless you do a lot of clever workarounds, you can only run one instance of the iOS simulator at a time. In our case, that is not a bad thing as we only have limited CPU power on the server anyway.

However it would be great if we could have a number of concurrent jobs running such that one could be checking source code out, one could be running tests on the simulator, and one could be uploading a build to a distribution service all at the same time.

To do this you need to have the Lockable Resources Plugin installed and then use the lock directive.

stage('Tests') {
    lock(resource: "simulator_${env.NODE_NAME}", inversePrecedence: true) {
      // reset the simulators before running tests
      sh "killall Simulator || true"
      sh "SNAPSHOT_FORCE_DELETE=yes snapshot reset_simulators"
      sh "fastlane tests"   

      step([$class: 'JUnitResultArchiver', testResults: 'build/reports/*.xml'])


stage('Build') {
    lock(resource: "compiler_${env.NODE_NAME}", inversePrecedence: true) {
      milestone 1
      sh "security list-keychains -s ~/Library/Keychains/iosbuilds.keychain-db"
      sh "security unlock-keychain -p ${env.KEYCHAIN_PASSWORD} /Users/iosbuilds/Library/Keychains/iosbuilds.keychain-db"
      if (isRelease()) {
        sh "fastlane build_release"
      } else {
        sh "fastlane build_alpha"

In this case we have two 'resources' one for the compiler and one for the simulator. We have suffixed these with the node name. This is because the resources are global across all build nodes and we want a lock per node.

Screenshot of concurrent builds in queue

The inversePrecedence argument means that the newest build will pass through first if there are multiple ones waiting. Combined with the milestone directive it means that if two builds are started at similar time that the newest one will pass through the milestone and the older one will be cancelled. This means we don't waste time building older build jobs if the build queue gets full with a lot of jobs (common when we are running a development sprint and have a lot of commits going on).

Automating Xcode 8’s New Automatic Signing

Picture of Matt speaking at SWMobile meetup

This was a talk I gave at the SWMobile Meetup in Bristol in October 2016. The talk was a lightning talk on automating the new Xcode 8 automated signing system when using it in a CI setup. In our case we use it with Jenkins and Fastlane to automate all ...

Changes to Keychains in macOS Sierra

I upgraded a build server to macOS Sierra and the keychain unlocking stopped working, here is how I fixed it.

Wiping the workspace in Jenkins 2.0 pipeline builds

Instead of the 'wipe workspace' checkbox that used to be in Jenkins, you can now use deleteDir() to clear the workspace before building.

WOTRA Trademark Scam letter

I filed for a trademark for my company name, shortly after it was accepted I received this scam letter in the post, quite a legitimate phishing attempt.

Using Xcode 8’s New Automatic Signing with Jenkins and Fastlane

Xcode 8 brings with it a new automatic code signing system. It is meant to make life a lot easier for developers, but needs a bit of work to get working with headless CI systems like Fastlane and Jenkins.

Uploading Git Changelog to Fabric Beta for Android Gradle Builds in Jenkins

The git changelog is not exposed as a variable in Jenkins for pipeline builds to use. This is how we got it and send it via Gradle to Fabric Beta when we distribute our automated builds

Global Build Numbers in Jenkins Multibranch Pipeline Builds

We wanted to have build numbers that were unique and incremental across all of our build jobs. Here is how I did it with a small python microservice.

Jenkins 2.0 and Multi-branch pipeline builds for iOS apps with Fastlane

Jenkins 2.0 beta is out and has included a multi-branch pipeline plugin that allows automatic build of feature branches from Github. Here is how I set it up to build feature branch builds of our iOS apps

Getting Proper UTF-8 Output From Fastlane on Jenkins 2.0 Pipeline builds

Jenkins 2.0 pipeline jobs get their locale from the master not slave, so you need to set the local on master to get UTF-8 output working correctly