Recent Blog Posts

Using MaxMind's free GeoIP databases with the official Docker PHP image

I recently had to add support for the MaxMind free GeoIP database to a PHP container build that was based on the official Docker PHP image on Docker Hub. Unfortunately, it seems nobody else who's added this support has documented it, so I figured I'd post this so that the next poor soul who needs to implement the functionality doesn't have to spend half a day doing it!

First, you need the PHP geoip extension, which is available via PECL (note: if you can make the PHP project itself use a composer library, there are a few better/more current geoip libraries available via Packagist!). Here's how to install it in one of the php 5.6 or 7.0-apache images (note that 7.1 uses Debian Stretch instead of Jessie... but the instructions should be the same there):

Patching or using a forked version of an Ansible Galaxy role

I maintain a lot of Ansible Galaxy roles. I probably have a problem, but I won't admit it, so I'll probably keep adding more roles :)

One thing I see quite often is someone submitting a simple Pull Request for one of my roles on GitHub, then checking in here and there asking if I have had a chance to merge it yet. I'm guessing people who end up doing this might not know about one of the best features of Ansible Galaxy (and more generally, open source!): you can fork the role and maintain your changes in the fork, and it's pretty easy to do.

I just had to do it for one project I'm working on. I am using the rvm_io.ruby role to install specific versions of Ruby on some servers. But there seems to have been a breaking change to the upstream packages RVM uses, summarized in this GitHub issue. I found a pretty simple fix (removing one array item from a variable), and submitted this PR.

Get started using Ansible AWX (Open Source Tower version) in one minute

Since yesterday's announcement that Ansible had released the code behind Ansible Tower, AWX, under an open source license, I've been working on an AWX Ansible role, a demo AWX Vagrant VM, and an AWX Ansible Container project.

As part of that last project, I have published two public Docker Hub images, awx_web and awx_task, which can be used with a docker-compose.yml file to build AWX locally in about as much time as it takes to download the Docker images:

Ansible open sources Ansible Tower with AWX

Ever since Red Hat acquired Ansible, I and many others have anticipated whether or when Ansible Tower would be open sourced. Ansible Tower is one of the nicest automation tools I've used... but since I haven't been on a project with the budget to support the Tower licensing fees, I have only used it for testing small-scale projects.

I wrote a guide for Automating your Automation with Ansible Tower, and it's both on the web and in Chapter 11 of Ansible for DevOps, and in the guide, I wrote:

For smaller teams, especially when everyone on the team is well-versed in how to use Ansible, YAML syntax, and follows security best practices with playbooks and variables files, using the CLI can be a sustainable approach... Ansible Tower provides a great mechanism for team-based Ansible usage.

Git gives 'ERROR: Repository not found.' when URL is correct and SSH key is used

I had a fun problem that made me spin my wheels an hour or so today. I was having no issue cloning a remote repository a number of times in the morning while debugging a Jenkins build job that runs a git clone + Docker image build and push operation.

Suddenly, when I was doing some final testing, I started to get the following:

git clone                            
Cloning into 'my-project'...
ERROR: Repository not found.
fatal: Could not read from remote repository.

Please make sure you have the correct access rights
and the repository exists.

I know that I had the repository's SSH key loaded (via eval "$(ssh-agent -s)" && ssh-add ~/.ssh/deploy-key), and if I unloaded the key, I would instead get:

Quick way to check if you're in AWS in an Ansible playbook

For many of my AWS-specific Ansible playbooks, I need to have some operations (e.g. AWS inspector agent, or special information lookups) run when the playbook is run inside AWS, but not run if it's being run on a local test VM or in my CI environment.

In the past, I would set up a global playbook variable like aws_environment: False, and set it manually to True when running the playbook against live AWS EC2 instances. But managing vars like aws_environment can get tiresome because if you forget to set it to the correct value, a playbook run can fail.

So instead, I'm now using the existence of AWS' internal instance metadata URL as a check for whether the playbook is being run inside AWS:


Subscribe to Jeff Geerling's Blog