Happy summer solstice! For the longest day of the year, welcome to a short blog post on using Ansible to automate the building of Docker images. This post is part of the blog series of posts, “Docker: Containers for the Masses”.
For the reader just joining, the previous posts in this series are:
- Introduction – Introduction to Docker
- Installation – Installation of Docker
- Using Docker – Using Docker
- Ansible and Docker – Using Ansible to manage Docker
Now that the basics of using Ansible to manage Docker have been introduced, particularly the Ansible docker
module, the next module to cover is the docker_image
module. The docker_image
module is an Ansible module that uses the Docker python client to connect to the Docker daemon (via a RESTful API) to build an images. This module, like any other module, can be creatively used in any playbook to build a Docker image that can be then run as a container.
Building Docker Images with Ansible
Refering to the post in this blog series on using Docker, examples showing how to build Docker images were given as well as covering the Dockerfile
. As the reader could see, there was a manual process to do this. A way of automating this is to use the Ansible docker_image
module.
Using this module is painfully simply. Well, not painful, but certainly simple!
A simple playbook:
- hosts: local
tasks:
- name: build Apache image
local_action:
module: docker_image
path: ../docker-image-source/ssh/
name: CaptTofu/apache
state: present
In the above example, as the YAML makes obvious, specifies using a local_action
(since this is not something you typically run across multiple hosts), the name of the docker_image
module, the path
to where the docker file is, the name
of the image and even more obvious the state
, in this case present
which means “yes, please build this!”.
When the playbook is run, the following output would be expected:
$ ansible-playbook -i hosts images.yml
PLAY [local] ******************************************************************
GATHERING FACTS ***************************************************************
ok: [localhost]
TASK: [build Apache image] ****************************************************
changed: [localhost]
PLAY RECAP ********************************************************************
localhost : ok=2 changed=1 unreachable=0 failed=0
And the build can be verified:
$ docker images
REPOSITORY TAG IMAGE ID CREATED VIRTUAL SIZE
CaptTofu/apache latest 3be6decea409 9 minutes ago 297.5 MB
A more interesting example
The above example was obviously very simple. A more interesting example can be found in the author’s git repository at https://github.com/CaptTofu/ansible-docker-presentation. This repository was used for recent attendence at AnsibleFest NYC 2014 to provide a practical example of using Ansible to do a number of things including building four different Docker images and then running those images as Docker containers across 45 HP Moonshot cartridges.
The repository contains several roles including an image_builder
role that has the following tasks:
---
- name: check or build ssh image
docker_image: path="/ssh/" name="/ssh" state=present
- name: check or build apache image
docker_image: path="/apache/" name="/apache" state=present
- name: check or build haproxy image
docker_image: path="/haproxy/" name="/haproxy" state=present
- name: check or build percona XtraDB Cluster image
docker_image: path="/pxc/" name="/pxc" state=present
The variables seen in this playbook task are set in the vars/main.yml
file:
---
images_source_path: /home/username/ansible_work/docker-image-source
repository_name: capttofu
NOTE: one can overwrite these variables using -e EXTRA_VARS
or long form --extra-vars=EXTRA_VARS
`.
The location of the Docker image source files is also available in a repo, . As is shown, https://github.com:CaptTofu/docker-image-source. The image source repo is checked out one directory up relative to where the playbook repository is located.
The playbook that is run that utilizes this role is very simple:
---
- hosts: localhost
roles:
- image_builder
And when run:
$ ansible-playbook -i hosts images.yml
PLAY [localhost] **************************************************************
GATHERING FACTS ***************************************************************
ok: [localhost]
TASK: [image_builder | check or build ssh image] ******************************
changed: [localhost]
TASK: [image_builder | check or build apache image] ***************************
changed: [localhost]
TASK: [image_builder | check or build haproxy image] **************************
changed: [localhost]
TASK: [image_builder | check or build percona XtraDB Cluster image] ***********
changed: [localhost]
PLAY RECAP ********************************************************************
localhost : ok=5 changed=4 unreachable=0 failed=0
One still will need to manually push built images to a private or the public Docker image registry. The previous blog posts cover how to do this.
Summary
This blog post demonstrated to the reader how to use Ansible to automate the building of Docker images using the Ansible docker_image
module. Starting with a simple example, and moving on to one more complex, the reader can gain a sense of how this can be used in an overall Ansible-based system to automate ensuring images that need to be run as containers will be available and if not, built for use.
Stay tuned for the next blog post on how to use the docker_facts
for gathering information and (other tricks) from a running fleet of containers.