Everything about Ansible Jinja2 Templating

Everything about Ansible Jinja2 Templating

Ansible uses Jinja2 templating to enable dynamic expressions and access to variables. Ansible includes a lot of specialized filters and tests for templating.

What is Jinja2?

Jinja2 is a templating language. It's designer friendly and widely used in the Python ecosystem. Few examples of applications using Jinja2 are Ansible, Django, Flask, Salt and Trac.

Why we need Jinja2 templating in Ansible?

When we manage a fleet of hundreds or thousands of servers of different OS configurations managing configurations on them becomes a tedious task as few parameters always differs from system to system and cluster to cluster.

Copying static files will not suffice in such situation. We need a solution which can dynamically takes the values as per the environment it is running on. And that's Jinja2.

Where the templating happens?

This all happens on your controller machine before the task is sent and executed on the target machine. We don't need jinja2 packages on target nodes. Only the information required by each task will be sent to remote nodes after template parsing.

What a jinja2 template looks like?

It's a file containing the configuration parameters. The values which are supposed to be different from cluster to cluster or system to system basis will be supplied dynamically through variables at the time of playbook execution.

Jinja2 Template Architecture

We use following tags in a Jinja2 template file:

  1. {{ }} : Used for embedding variables which prints their actual value during code execution.
  2. {% %} : Used for control statements such as loops and if-else statements.
  3. {# #} : To specify the comments.

Template files ends with .j2 extension.

Ansible template module

Ansible’s template module transfers template files to remote hosts while playbook execution. It works similarly to the copy module.

We use template module instead of copy in cases where we need to transfer application configuration files with dynamic content, such as the NGINX or Apache server blocks.

Example of template file basic usage

I have a playbook which deploys webserver on CentOS.

---
- hosts: worker1
  become: yes
  vars:
    company_name: LearnCodeOnline
  tasks:

  - name: Install httpd Package
    yum: name=httpd state=latest


  - name: Copy the customized index.html file
    template: src=index.html.j2 dest=/var/www/html/index.html mode=0775
    notify:
    - restart and enable httpd

  handlers:
    - name: restart and enable httpd
      become: true
      service:
        name: httpd
        state: restarted
        enabled: yes

Our playbook is using template module to copy our index.html.j2 template file to worker1 node.

Here is our template file which is present on the same directory as our playbook file.

templates $ cat index.html.j2
<html>
    <center>
        <h1> Welcome to {{ company_name }}. This webserver is hosted on {{ ansible_hostname }}. </h1>
    </center>
</html>

Here we are using two variables which will be replaced by their actual values (one (company_name) is defined within playbook itself and another is an Ansible fact variable (ansible_hostname )) during execution.

Let us execute the playbook.

templates $ ansible-playbook -i myinventory httpd_deployment.yml -kK

templates-1.png

Now let us verify the content by querying the website's landing page.

templates $ curl worker1:80
<html>
    <center>
        <h1> Welcome to LearnCodeOnline. This webserver is hosted on lco-worker1. </h1>
    </center>
</html>

That's working great! Both the variables have been replaced with by their actual values dynamically.

Example of template file usage with conditionals

Conditional statements such as for loops can be used within Jinja2 template files to iterate over a list of items.

Example template file:

---
- hosts: worker1
  become: yes
  vars:
    usernames: ['Alice', 'Bob', 'John', 'Martin', 'Alex']

  tasks:
    - name: Loops usage within Jinja2 templates
      template:
        src: usernames.j2
        dest: /home/ansible_user/usernames.txt

Here is our template file.

templates $ cat usernames.j2
The list of users who are going to be part of the ongoing migration process.

{% for item in usernames %}

   {{ item }}

{% endfor %}

Let us execute the playbook now.

templates $ ansible-playbook -i myinventory username.yml -kK

templates-loops.png

Now verify the the content of that file.

templates $ ansible -i myinventory worker1 -m shell -a "cat /home/ansible_user/usernames.txt" -b -kK

templates-loops-2.png

That's all for this article now.

To understand more about Jinja2 templating please refer official documentation here .

Hope you like the article. Stay Tuned for more.

Thank you. Happy learning!

Did you find this article valuable?

Support Learn Code Online by becoming a sponsor. Any amount is appreciated!