Using Ansible and GitOps to Manage the Lifecycle of a Containerized Application
Using Ansible and GitOps to Manage the Lifecycle of a Containerized Application
One of the great advantages of combining GitOps with Ansible is that you get to streamline the automation delivery and the lifecycle of a containerized application.
With the abilities of GitOps we get to:
- Standardize configurations of our applications.
- Inherit the benefits of version control of our configurations.
- Easily track changes of the configuration settings making fixing issues easier.
- Have one source of truth for our applications.
Combine the above with Ansible and you have everything you need to accomplish configuration consistency for a containerized app anywhere that you automate.
That leads us to, "how do we combine Ansible and GitOps to manage the lifecycle of a containerized application?"
Simple. By creating an Ansible workflow that is associated with a Git webhook that is part of my application's repository.
What is a Git webhook you ask?
Git webhooks are defined as a method to deliver notifications to an external web server whenever certain actions occur on a repository.
For example, when a repository is updated, this could trigger an event that could trigger CI builds, deploy an environment, or in our case, modify the configuration of our containerized application.
A webhook provides the ability to execute specified commands between apps over the web. Automation controller provides webhook integration with GitHub and GitLab, but for the purposes of this blog we will be integrating with GitHub.
In the following sections of this blog, I'm going to provide the step-by-step process to:
- Setup your Git webhook (using GitHub).
- Setting up an Ansible workflow that triggers via push events from your GitHub repository.
Create a GitHub personal access token
The GitHub personal access token (PAT) is one of the credentials needed to associate the Ansible workflow with your Git repository.
Generate a personal access token (PAT) for use with automation controller.
- In the profile settings of your GitHub account, click Settings.
- Below the Personal settings, click Developer Settings.
- In the Developer settings, click Personal access tokens.
- From the Personal access tokens screen, click Generate new token button.
- When prompted, enter your GitHub account password to continue.
- In the Note field, enter a brief description about what this PAT will be used for.
- In the Expiration drop down, select No expiration.
- In the Scope fields, automation controller webhook only needs repo scope access, with the exception of invites. For information about other scopes, click the link right above the table to access the docs.
Click the Generate Token button at the bottom of the page.
Once we have our PAT in place, the next step is to create a Git repository that will be triggered by our GitHub webhooks when changes are made to the repository.
For the purposes of this blog, I'll be using my App Demo Repository. Feel free to use your own or fork this repository to follow along.
Familiarizing ourselves with the App Demo Repository
The App Demo Repository is fairly simplistic, as it contains:
container_playbook.yml
group_vars/all.yml
requirements.yml
The container_playbook.yml is a simple playbook that creates a color
container, starts it on a specific port and sets two environment
variables, APP_COLOR
and tree
.
A sample of that container_playbook.yml
:
--- - name: Playbook to setup prereqs hosts: all become: true tasks: - name: Create a color container containers.podman.podman_container: name: colors image: docker.io/mmumshad/simple-webapp-color:latest state: started network: host ports: - "{{ host_port }}:{{ container_port }}" env: APP_COLOR: "{{ color }}" tree: "{{ tree }}"
The group_vars/all.yml
is where I'll be making modifications to my
Podman container that will trigger changes to the container.
A sample of that group_vars/all.yml
file:
color: "BLUE" tree: "trunk" host_port: 8080 container_port: 8080
Finally, we have the requirements.yml
file that ensures we have the
containers.podman collection available to use within the playbook.
A sample of the requirements.yml
:
collections: - name: containers.podman
With our repository in place and our GitHub PAT set, the next steps involve creating our Red Hat Ansible Automation Platform resources that will be triggered when GitHub push events happen in the App Demo Repository.
Creating our Ansible Automation Platform Resources
Within my automation controller dashboard, I first need to create my credential resources to ensure that when I create my new project, workflow and job template -- they can all easily attach my App Demo PAT credential.
Within the automation controller dashboard:
- Under Resources > Credentials click the blue Add button.
- Provide a Name, e.g. App Demo PAT.
- Select GitHub Personal Access Token as the Credential Type.
- Within Type Details, add the secret using the previously generated token from GitHub.
- Click Save.
Once my App Demo PAT credential is in place, I need an additional credential to access my host that will be running the Podman container. In my case, this is an AWS instance.
In order to access this host, I will create a new credential that stores my AWS private key.
- Under Resources > Credentials click the blue Add button.
- Provide a Name, e.g. My AWS Private Key.
- Select Machine as the Credential Type.
- Within Type Details, add the SSH Private Key in the text area.
- Click Save.
Once the credentials are in place, I need to create an inventory that stores the details of my AWS instance.
To add details of my AWS instance, I will create an inventory file.
- Under Resources > Inventories click the blue Add > Add inventory button.
- Provide a Name, e.g. App Demo Inventory.
- Click Save.
- Under Resources > Inventories click App Demo Inventory.
- Click the tab labeled Hosts and click the Add button.
- Provide a Name, e.g. App Demo Host.
Within Variables, provide the following YAML:
--- ansible_host: ansible_user: ec2-user
With the credentials and inventory resources set, I will create my App Demo project. The purpose of this project is to create a workflow that contains a job template that automatically runs every time an update to the App Demo repository takes place.
This ensures that as I make changes to my Podman container settings within my Git repository, the container_playbook.yml runs to make the appropriate changes.
Within the automation controller dashboard:
- Under Resources > Projects click the blue Add button.
- Provide a Name, e.g. App Demo Project.
- Select Default as the Organization.
- Select Default execution environment as the Execution Environment.
- Select Git as the Source Control Credential Type.
- Within Type Details, add the Source Control URL (your GitHub repository).
- Within Options, select Clean, Delete, Update Revision on Launch.
- Click Save.
Next, create a workflow template.
- Under Resources > Templates click the blue Add > Add workflow template.
- Provide a Name, e.g. App Demo Workflow.
- Within Options, checkmark Enable Webhook.
- Within Webhook details, select GitHub as the Webhook Service.
- Within Webhook details, select your GitHub PAT token previously created as the Webhook Credential, e.g. App Demo PAT.
- Click Save.
- Within the Please click the Start button to begin window, click Save at the top right corner.
- Copy the Webhook URL and the Webhook Key as they will be used later.
Enabling GitHub Webhooks for the App Demo Repository
With the Ansible Automation Platform workflow template created and the GitHub repository with the required files in place, the next step is to enable webhooks for our repository, e.g. app_demo.
- At the homepage of your GitHub repository, select the Settings tab.
- Within the Settings tab, select Webhooks.
- Within the Webhooks section, select the Add webhook button.
- Enter the Payload URL (Webhook URL of the workflow).
- Change the Content type drop down to application/json.
- Enter the Secret (Webhook key of the workflow).
- Leave the defaults to use push events, and click the button Add webhook.
By default, GitHub verifies SSL certificates when delivering payloads. If your automation controller SSL certificates are not signed, ensure to disableSSL verification.
Creating the App Demo job template
The App Demo job template runs the container_playbook.yml file automatically every time an update to the Git repository takes place.
To create the job template within your automation controller dashboard:
- Under Resources > Templates click the blue Add > Add job template.
- Provide a Name, e.g. App Demo Job.
- Select Run as the Job Type.
- Select App Demo Inventory as the Inventory.
- Select App Demo Project as the Project.
- Select Default execution environment as the Execution Environment.
- Select container_playbook.yml as the Playbook.
- Select Credentials and select My AWS Private Key.
- Within Options, select Enable webhook.
- Select GitHub as the Webhook Service.
- Select your GitHub PAT token previously created as the Webhook Credential, e.g. App Demo PAT.
- Click Save.
Updating the created App Demo Workflow
Previously, the App Demo workflow was created. The purpose of this workflow is to ensure that the App Demo Project is always in sync and that the App Demo Job runs the container playbook whenever changes are made to the App Demo repository.
- Under Resources > Templates, select your template. e.g App Demo Workflow.
- Within the Details section, select the Visualizer tab and click the green Start.
- For Node Type select Project Sync and select the appropriate project, e.g. App Demo Project and click Save.
- Hover over the App Demo Project and select the plus "+" symbol.
- Within the Add Node window, select On Success as to when this node should be executed and click Next.
- Select the App Demo Job as the Node Type and click Save.
- Once brought back to the Visualizer, select the Save button at the top right corner.
Verify App Demo Setup
To test if all is working correctly, head to your host that is running the Podman container. Once there, the following podman ps command can be run:
$ sudo podman ps CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
NOTE: The first time you run podman ps, you should have no containers running as you haven't run the App Demo workflow.
Head over to your App Demo GitHub repository and modify the
app_demo/group_vars/all.yml
file where you change the color: "BLUE" to
color: "YELLOW" and git push your changes.
Head over to your automation controller dashboard and you should see the App Demo workflow running. Once complete, within your host, verify the container has the changes made:
$ ssh -i </path/to/private-key.pem> ec2-user@<IP> $ sudo podman exec -it colors env PATH=/usr/local/bin:/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin TERM=xterm container=podman PYTHON_VERSION=3.7.0 PYTHON_PIP_VERSION=18.0 LANG=C.UTF-8 GPG_KEY=0D96DF4D4110E5C43FBFB17A2A347FA6AA65421D APP_COLOR=YELLOW tree=trunk HOME=/root
Notice how the Podman container is now running and has the color YELLOW.
Going back to the App Demo repository, change the color from YELLOW to GREEN and git push your changes.
The automation controller dashboard will run the App Demo workflow and once complete, you can re-run the same exec command from your host and see the color has now changed to GREEN.
$ ssh -i </path/to/private-key.pem> ec2-user@<IP> $ sudo podman exec -it colors env PATH=/usr/local/bin:/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin TERM=xterm container=podman PYTHON_VERSION=3.7.0 PYTHON_PIP_VERSION=18.0 LANG=C.UTF-8 GPG_KEY=0D96DF4D4110E5C43FBFB17A2A347FA6AA65421D APP_COLOR=GREEN tree=trunk HOME=/root
Conclusion
The goal of this exercise was to show the power of Ansible and GitOps. Together, they can provide key automation to your containerized applications.
While in the demo we made a simplistic color value change of our application, but imagine we applied this for:
- patching our application because of a security threat.
- updating our application to a newer version.
- managing containerized applications at the edge.
And all this doesn't even mention the inherited benefits of:
- Standardizing configurations of our applications.
- Inheriting the benefits of version control of our configurations.
- Easily tracking changes of the configuration settings making fixing issues easier.
- Have one source of truth for our applications.
The use cases and abilities that both tools provide together are endless.