Deploying to Flynn from Travis.CI

ci flynn gitops 
↞ See all posts

In my previous post, I shared some tips on creating a production Flynn cluster. If you don’t know, Flynn is a an open-source self-hosted Heroku replacement (PASS).

In this article, I’ll share some tips on how to set up continuous integration using Travis.CI and you Flynn server. This project assumes you already have your project’s test suite running automatically on Travis.CI.

To understand how this process works, you will need to understand Flynn’s git security model. When you install the Flynn client on your development machine and connect to your cluster, Flynn stores a cluster key in a file ( ~/.flynnrc ) which is used to authenticate to the server. All Flynn users on your cluster share this key. Flynn also has a helper which stores this key in your OSX Keychain (or equivalent system-level keystore) so that when you git push, the credentials will be used.

However, you don’t need to use this system-level keystore if you configure your git remote to include the username and password directly. There is a secure way to do this on Travis! You also do not need the Flynn CLI tool.

First, you’ll need the Travis ruby gem installed:

1gem install travis

Then, you’ll be using the gem to encrypt your Flynn cluster Key (which you can find in ~/.flynnrc. Travis lets you store encrypted data within your project’s .travis.yml configuration file. This allows you to share your project with no worry that anyone other than the Travis severs can deploy to your cluster.

1travis encrypt FLYNN_KEY=XXXXXXX

Now take that encrypted output and add it to your project’s .travis.yml under the secure directive.

Next, we’ll use the Travis’ after-success lifecycle event to tell Travis to push our now-tested branch to the server:

1after_success: 2 - git pull 3 - git remote add flynn [https://user:$](https://user:$ 4 - git push flynn master

A complete file for a Node.js project would look like:

1sudo: false 2language: node_js 3node_js: 4 - "6" 5env: 6 - secure: "YYYYYYYYYYYYYYY=" 7after_success: 8 - git pull 9 - git remote add flynn https://user:$ || true 10 - git push flynn master 11script: npm run test

And that’s it! Travis will now deploy to Flynn in a secure way after every green build.

Advanced Topics:

Deploying only after all steps in a build matrix have complete

With Travis, it is possible to run your test suite a few times with separate configurations. Perhaps you want to run a test once with MySQL and once with Postgres… you can! Travis calls this feature the Build Matrix. You can configure separate collections of environment variables to control your test behavior.

However, there is no built-in way for Travis to expose what would amount to an after-build-matrix-success directive in the configuration .travis.yml. Luckily, someone has solved this problem for us: [travis-after-all]( Travis-after-all is a cool little Node.js package which polls Travis’ internal APIs to tell when all parts of your build matrix have complete, and then run your deploy script once-and-only-once. Modify your deployment scripts in the ways described by the project’s Readme, and you should be good to go!

Custom Branches = Custom Deployments

You may only want to deploy to your Flynn cluster when certain branches are tested. Perhaps master should be deployed to and production should be deployed to When testing on Travis, you have a few environment variables exposed to you, such as: TRAVIS_BRANCH which you can use to make decisions about how to deploy.

The example I described above would look like:

1sudo: false 2language: node_js 3node_js: 4 - "6" 5 6env: 7 - secure: "xxxxxxxxxx=" 8 9after_success: 10 - | 11 FLYNN_APP="" 12 if [ "$TRAVIS_BRANCH" = "master" ]; then FLYNN_APP="www-staging"; fi 13 if [ "$TRAVIS_BRANCH" = "production" ]; then FLYNN_APP="www"; fi 14 if [ "$FLYNN_APP" = "" ]; then 15 echo "skipping branch $TRAVIS_BRANCH" 16 else 17 git pull 18 git remote add flynn https://user:$$FLYNN_APP.git 19 git push flynn master 20 fi 21script: npm run test

(why yes, you can write bash directly in your .travis.yml file!)

Hi, I'm Evan

I write about Technology, Software, and Startups. I use my Product Management, Software Engineering, and Leadership skills to build teams that create world-class digital products.

Get in touch