Benjamin Guttmann
Published at 14.02.2016
Setting up a local Concourse CI and creating a Dockerfile pipeline.
Welcome to the third part of our series concerning Concourse CI and Docker.
In the first one you got a brief overview about Concourse CI in general and a very quick ‘getting started’ guide for Docker.
The second part was about writing an independent Dockerfile, building Docker images and pushing them to Docker Hub.
Well, that’s enough of Docker for the moment, let’s get back to Concourse CI.
Table of Contents
We will use Vagrant to get our Concourse instance running, so please get Vagrant and install it.
So, let’s go. Open a terminal and create a new directory.
After that, you can access the web server via the IP 192.168.100.4:8080
On the main page you can download the Fly CLI for your operating system, please do so.
One small remark, if you’re on Linux or OS X, you will have to chmod +x the downloaded binary and put it in your $PATH.
As you might see, there are currently no pipelines configured, we will change this in a moment.
Just to make it clear, this is a very simple example without fancy Dockerfiles and so on, the goal is to make it clear how Concourse CI works in general, please keep this in mind.
For this part I made small changes to the Dockerfile of part two, I removed the install git command and the app will not be cloned and started now. You can get the new Dockerfile from Github.
Before we start with our pipeline, it’s good to know some facts about the base concepts of Concourse CI. The three core concepts are named tasks, jobs and resources, let’s take a brief look at each one.
A job describes some actions to be performed, when dependent resources change or when they are triggered manually. You can define jobs that run unit tests whenever a new code is pushed to a specified repository.
Jobs are functions which automatically run when there are new inputs available. A job can depend on the outputs of another job, that is why we need to build a pipeline.
The actions that need to be performed are defined in a so-called Build Plan. In such a plan you can express everything, e. g. running simple unit tests or execute a huge amount of tasks and aggregate the results.
In the Concourse CI world the execution of a script in an isolated environment is called task. That means the script will be executed in a Docker Container with some parameters.
The execution of the script decides if the task succeeds or not, i.e. exit code 0 is success, otherwise it is fail.
You can use the “Fly” command line tool to execute a task manually or you can let a job do that for you. Both the job and “Fly” will execute the same configuration that will give you the guarantee that if you execute tasks locally with Fly, the tasks will run the same way as they would in your pipeline.
In general, tasks run as unprivileged users but you can let Fly or your job execute the task as root user. A task cannot configure itself to be run as root, please take a note of that fact.
In general, a resource in Concourse doesn’t have to be something special. There are just a few requirements to meet in order to be a resource in Concourse: it must be possible to check for updated versions of the entity, it should be possible to pull down some specific version and/or push up to create new versions. An example for such a resource that most of us may know would be a git repository.
The best way to get to know which resources you can use, is to take a look at the Concourse GitHub organization and search through..
Well, enough of the boring (but important) basics, let’s get our first pipeline started.
First of all, we need to make some preparations before we can finally start to create our pipeline.
Now, we will start with our „pipeline.yml“, first thing we will do is to add a resource.
resources:
-name: anynines_blog_dockerfile
type: git
source:
uri: https://github.com/benjaminguttmann-avtq/concourse_ci_blog.git or if you want to check out via ssh git@github.com:benjaminguttmann-avtq/concourse_ci_blog.git
branch: master
paths: [Dockerfile]
Please double-check the indentation of your file because it is a YAML file and it is very ruthless when it comes to unnecessary white spaces and things like that.
Your pipeline.yml should now look something like this:
resources:
We want to push our Docker image to Docker Hub, after it was build for this reason we need to define another resource directly under the git resource.
– name: anynines_blog_build_image
type: docker-image
source:
repository: bguttmannavtq/anynines-blog-build-image
email: {{DOCKER_MAIL}}
username: {{DOCKER_USER}}
password: {{DOCKER_PASS}}
As I mentioned before, there are different types of resources in Concourse. The first resource we used was a git-resource, that is a git repository where you can get code from or push code to. The second resource is of docker-image type, that means we specify a repository at Docker Hub where we can get a Docker Image from or push a Docker Image to. If you want to know more about the resources just click on the types above and you will be redirected to the Github repositories.
This is what your pipeline.yml is now looking like:
resources:
The next step is adding a job that builds our Docker Image from our Dockerfile.
jobs:
– name: anynines_blog_build_job
plan:
– get: anynines_blog_dockerfile
trigger: true
– put: anynines-blog-build-image
params: {build: anynines-blog-dockerfile}
Once again please keep an eye on the indentations of the file.
At this point, your file should look something similar to this:
jobs:
This kind of YAML would work perfectly with a public Github repository, but what if you want to use a private Github repository as a resource? Not a problem, there are just a few things you have to add to get this to work as well.
In your pipeline.yml add a private_key to the source, you can do this in two ways:
resources:
resources:
The credentials.yml should look something like this:
DOCKER_USER: dockerhub-username DOCKER_MAIL: dockerhub-email DOCKER_PASS: dockerhub-password
git-private-key: | -----BEGIN RSA PRIVATE KEY----- Add your private key here -----END RSA PRIVATE KEY——
If you want to use a ssh key please make sure that your key has no passphrase; keys with passphrases are not supported by Concourse CI.
After we finished writing our pipeline let’s get it to work, switch to your command line (cd to the directory where your pipeline.yml is) and enter the words
fly set-pipeline -p docker-images-pipeline -c pipeline.yml -l credentials.yml
If you got an error like „failed to load variables from file ( ): yaml: line 1: found character that cannot start any token“, please check if you used white spaces instead of tabs for indentation in your YAML files. Perhaps you used some „special“ symbols, e.g. in your password please set them into quotes. This should solve the issue.
Refresh the Concourse main page (192.168.100.4:8080) and now you should see your pipeline.
Unpause your pipeline by pressing the play-button in the UI or by writing:
fly unpause-pipeline -p docker-images-pipeline
to the command line.
After pushing something new to your resource repo the pipeline will start and build the Docker Image and afterwards, push the image to Docker Hub. I think that is more than enough as for this time.
In the last part of our series about Concourse CI and Docker we will take a look at testing an application in a Docker container built of our Docker Image and ways to deploy it afterwards.
© anynines GmbH 2024
Products & Services
© anynines GmbH 2024