Jinja2 Template and Dictionary issue

346 views
Skip to first unread message

Owen Corcoran

unread,
Feb 14, 2018, 11:07:00 AM2/14/18
to Ansible Project
 

Can anyone help me with the below, maybe my approach is wrong. What I’m trying to do is to create from a template a keepalived file based on the elements in a dictionary.

 

I’ve included the code below, when its ran the error that appears is

 

                msg": "AnsibleUndefinedVariable: 'dict object' has no attribute 'hostname'"

 

The error appears to in the second loop in the jinja2 template, where i try to extract the elements from the sub lst in the dictionary.

 

ANSIBLE Dictionary

 

keepalived_virtual_ip:

  - vip_details_1:

    haproxy_vip_name: "AddressCleaner_Development"

    ip: "1.0.1.2"

    front_end_port: 80

    haproxy_backend_servers:

       - servers_1.1:

          hostname: system12

          address: 2.0.0.1

       - servers_1.2:

          hostname: system13

          address: 2.0.0.2

 

  - vip_details_2:

    haproxy_vip_name: "AddressCleaner_Cert"

    ip: "3.0.0.114"

    front_end_port: 80

    haproxy_backend_servers:

       - servers_2.1:

          hostname: system21

          address: 2.0.0.3

       - servers_2.2:

          hostname: system22

          address: 2.0.0.4

 

 

 

keepalived_virtual_ip:

  - vip_details_1:

    haproxy_vip_name: "AddressCleaner_Development"

    ip: "3.0.0.115"

    front_end_port: 80

    haproxy_backend_servers:

       - servers_1.1:

          hostname: lonldpostal01

          address: 3.0.0.87

       - servers_1.2:

          hostname: lonldpostal02

          address: 3.0.0.100

 

  - vip_details_2:

    haproxy_vip_name: "AddressCleaner_Cert"

    ip: "3.0.0.114"

    front_end_port: 80

    haproxy_backend_servers:

       - servers_2.1:

          hostname: lonlcpostal01

          address: 3.0.0.96

       - servers_2.2:

          hostname: lonlcpostal02

          address: 3.0.0.104

 

 

 

 

HA PROXY TEMPLATE

 

 

{% for item in keepalived_virtual_ip %}

 

   listen {{ item.haproxy_vip_name }} {{ item.ip }}:{{ item.front_end_port }}

      mode {{ haproxy_mode }}

      balance {{ haproxy_vip_algo }}

   default_backend {{ item.haproxy_vip_name }}_backend

 

{% endfor %}

 

 

 

{% for item in keepalived_virtual_ip %}

backend {{ item.haproxy_vip_name }}_backend

    mode tcp

    balance source

 

    {% for backend in item.haproxy_backend_servers %}

       server {{ backend.hostname }} {{ backend.address }}:{{ haproxy_vip_port }} maxconn 9000 send-proxy check

    {% endfor %}

 

{% endfor %}

 

Kai Stian Olstad

unread,
Feb 14, 2018, 1:36:31 PM2/14/18
to ansible...@googlegroups.com
On Wednesday, 14 February 2018 17.07.00 CET Owen Corcoran wrote:
> keepalived_virtual_ip:
> - vip_details_1:
> haproxy_vip_name: "AddressCleaner_Development"
> ip: "1.0.1.2"
> front_end_port: 80
> haproxy_backend_servers:
> - servers_1.1:
> hostname: system12
> address: 2.0.0.1
> - servers_1.2:
> hostname: system13
> address: 2.0.0.2
>

It's not allowed to have . (dot) in variable name only letters, numbers and underscores is allowed so servers_1.1: is invalid


> {% for item in keepalived_virtual_ip %}
> backend {{ item.haproxy_vip_name }}_backend
> mode tcp
> balance source
> {% for backend in item.haproxy_backend_servers %}
> server {{ backend.hostname }} {{ backend.address }}:{{ haproxy_vip_port }} maxconn 9000 send-proxy check
> {% endfor %}
> {% endfor %}
>

Lets say that servers_1.1: is servers_1_1:, the same for server_1.2


item.haproxy_backend_server is a list of dictonary, the hostname is not backend.hostname but
backend.servers_1_1.hostname and backend.servers_1_2.hostname


--
Kai Stian Olstad

Owen Corcoran

unread,
Feb 14, 2018, 3:55:08 PM2/14/18
to ansible...@googlegroups.com
Could i have instead of :

Servers_1.1
Servers_1.2
Servers_2.1
Servers_2.2
Servers_3.1
Servers_3.2


Call each list

servers

The reason being i dont want to have to hard code names in the jinja2 template of the elements in the lists of backends, depending on the size of the dictionary i might shink or add hosts/backends and i want the template to dynamically pick these additions or substractions without a code change in the template file.


--
You received this message because you are subscribed to a topic in the Google Groups "Ansible Project" group.
To unsubscribe from this topic, visit https://groups.google.com/d/topic/ansible-project/JsvtwiHeyvE/unsubscribe.
To unsubscribe from this group and all its topics, send an email to ansible-project+unsubscribe@googlegroups.com.
To post to this group, send email to ansible-project@googlegroups.com.
To view this discussion on the web visit https://groups.google.com/d/msgid/ansible-project/3490142.gy42nNLA3x%40x1.
For more options, visit https://groups.google.com/d/optout.



--
Thanks
Owen Corcoran

Kai Stian Olstad

unread,
Feb 15, 2018, 1:02:39 AM2/15/18
to ansible...@googlegroups.com
On 14.02.2018 21:54, Owen Corcoran wrote:
> Could i have instead of :
>
>
> Servers_1.1
> Servers_1.2
> Servers_2.1
> Servers_2.2
> Servers_3.1
> Servers_3.2
>
>
> Call each list
>
> servers

The easiest to do is make haproxy_backend_servers a list of dictionaries
and not a list of dictionary.

So if you can change you haproxy_backend_servers to

haproxy_backend_servers:
- name: servers_1.1
hostname: system12
address: 2.0.0.1
- name: servers_1.2:
hostname: system13
address: 2.0.0.2

You code will work as is since you can call backend.hostname and not
backend.<something>.hostname


--
Kai Stian Olstad
Reply all
Reply to author
Forward
0 new messages