I've got a task (actually a role, but using a task here to make the example easier) that I don't own which does some operations on a variable. It assumes the variable is an integer. I need to somehow pass it a variable and have it come through as an int, and I'm not having any luck.
Here is a super simplified version of the task that I don't own:
frob.yml
- name: Validate that frob_count is <= 100
fail: msg="{{frob_count}} is greater than 100"
when: frob_count > 100
- name: Do real work
debug: msg="We frobbed {{frob_count}} times!"
My playbook is:
- name: Frob some things
hosts: localhost
vars:
things:
- parameter: 1
- parameter: 2
- parameter: 45
tasks:
- with_items: "{{things}}"
include: frob.yml
vars:
frob_count: "{{item.parameter}}"
No matter what, I get errors like "1 is greater than 100" from frob.yml
. Looks like it's getting the var as a string instead of an integer.
I've tried stuff like frob_count: "{{item.parameter | int}}"
with no luck. If I could change frob.yml
it'd be easy, but like I said, that's out of my control. Any thoughts?
This is on Ansible 2.6.4
Solution
Upgrade to Ansible 2.7 (currently available as the stable-2.7
branch, scheduled for GA on Oct. 4th, 2018).
Add jinja2_native=True
to the [defaults]
section of the ansible.cfg
(or set an environment variable ANSIBLE_JINJA2_NATIVE=True
.
Leave your code as in the question (i.e., frob_count: "{{item.parameter}}"
).
The result:
TASK [Do real work] **********************************************************************************************************************
ok: [localhost] => {
"msg": "We frobbed 1 times!"
}
TASK [Validate that frob_count is <= 100] ************************************************************************************************
skipping: [localhost]
TASK [Do real work] **********************************************************************************************************************
ok: [localhost] => {
"msg": "We frobbed 2 times!"
}
TASK [Validate that frob_count is <= 100] ************************************************************************************************
skipping: [localhost]
TASK [Do real work] **********************************************************************************************************************
ok: [localhost] => {
"msg": "We frobbed 45 times!"
}
Explanation
Currently any value returned by Jinja2 template is a string, so even if you used the int
filter inside (as in {{item.parameter | int}}
) the output is always rendered to a string by Ansible.
Ansible 2.7 will use (with the above parameter) a feature of Jinja 2.10 called Native Python Types and retain the data type.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With