Over the last few years I have written a number of Ansible roles that I have published on Galaxy. When I wrote them, I followed the Jeff Geerling’s pattern for testing ansible roles with Travis CI so that I could put a badge in Galaxy that they were working. When I was introduced to Molecule earlier this year, I decided to migrate my current roles to use molecule as the testing framework. It has a lot more features available to it, including being able to actually test it before you check it in, not afterwards like with the Travis CI setup.
Initialize the Scenario
Since the role already exists, we need to initialize a scenario with Molecule, rather than a role (which does essentially the same think as ansible-galaxy init
does). So the first step is to check out the role from source control.
git clone git@github.com:austincloudguru/ansible-role-splunk-forwarder.git
Once the code is checked out, you need to change directories into the role and run the molecule init scenario
command to create the molecule scenario.
cd ansible-role-splunk-forwarder
molecule init scenario —scenario-name default —role-name ansible-role-splunk-forwarder -d docker
This will create the scaffolding for molecule inside the role using docker as the default driver. There are multiple drivers and you can have multiple scenarios. I have one set of roles that includes docker as the default, but also can be tested in scenarios configured with AWS and GCP (this can be useful since each cloud provider image can have different packages and settings).
Configuring Molecule
For all the roles that I create, I make some changes to the default Molecule files. I add a yamllint.yml file that contains the following to make some changes to the default yamllint settings.
---
extends: default
rules:
line-length:
max: 120
level: warning
truthy: disable
I also update the dockerfile.j2 file and add some additional packages (iproute2 systemd unzip) to the apt-get blocks. This allows me to pull down base images directly from providers (ubuntu, centos) instead of building my own base images and then having molecule build on top of them.
#ubuntu
RUN if [ $(command -v apt-get) ]; then apt-get update && apt-get install -y python sudo bash ca-certificates iproute2 systemd unzip && apt-get clean; \
Finally, I update the molecule.yml file to use the yamllint.yml file and configure the docker containers (platforms) that I want to run the molecule tests against.
---
dependency:
name: galaxy
driver:
name: docker
lint:
name: yamllint
options:
config-file: molecule/default/yamllint.yml
platforms:
- name: ubuntu-18.04
image: ubuntu:18.04
privileged: True
command: /sbin/init
- name: centos-7
image: centos:7
privileged: True
command: /sbin/init
provisioner:
name: ansible
lint:
name: ansible-lint
scenario:
name: default
verifier:
name: testinfra
lint:
name: flake8
Running Tests
Before you run your first full test of the role, I suggest you run molecule lint
to make sure everything passes. This will allow you to quickly see the issues without having to scroll back up. Once you have validated that the linting is good, you can run `molecule test</code> and see if you have any other errors or issues around idempotence.
You can also add some additional tests in the test_default.py file that you can run after the ansible is complete. The following validates that the user and group is setup and that the service is enabled and running.
import os
import testinfra.utils.ansible_runner
testinfra_hosts = testinfra.utils.ansible_runner.AnsibleRunner(
os.environ['MOLECULE_INVENTORY_FILE']).get_hosts('all')
def test_splunk_group_exists(host):
splunk_group = host.group("splunk")
assert splunk_group.exists
def test_splunk_user_exists(host):
splunk_user = host.user("splunk")
assert splunk_user.exists
def test_splunk_is_running(host):
splunk_service = host.service('splunkd')
assert splunk_service.is_running
assert splunk_service.is_enabled
Continuous Integration
If you would like to still test the role with TravisCI or be able to post back to Ansible Galaxy that the build is passing, you can run the Molecule tests via TravisCI by replacing your current .travis.yml file with the following.
---
sudo: required
language: python
cache: pip
branches:
only:
- master
services:
- docker
before_install:
- curl -fsSL https://download.docker.com/linux/ubuntu/gpg | sudo apt-key add -
- sudo add-apt-repository "deb [arch=amd64] https://download.docker.com/linux/ubuntu $(lsb_release -cs) stable"
- sudo apt-get update
- sudo apt-get -y install docker-ce
install:
- pip install molecule docker
script:
- molecule test
notifications:
webhooks: https://galaxy.ansible.com/api/v1/notifications/
That’s all there is to it. Now you can run the molecule test
command locally prior to checking in your code to validate that it works properly as well as have it run in TravisCI so that it can update the status on Ansible Galaxy.
Comments