I have developed a playbooks that sends a mail indicating a list of 3-zero-padded numbers.
I want to make the padding in the for loop which prints the information in the mail body.
The playbook takes the number to pad from variable hostvars[host]['number']
.
The padding is made via the Ansible syntax
myhost-{{ 'd' % hostvars[host]['number']|int }}
as you can see in the following task.
Now, I would like to do the padding via Python, because later I want to make more formatting operations on each element printed by the loop.
So I have tried to substitute the upper line with
{{ "myhost-" str(hostvars[host]['number']).zfill(3) }}
but I am getting this error:
Sending e-mail report...
localhost failed | msg: The task includes an option with an undefined variable. The error was: 'str' is undefined
So I tryed to substitute it (as suggested in comments of this question) with
myhost-{{ hostvars[host].number.zfill(3) }}
but now I get
Sending e-mail report...
localhost failed: {
"msg": "The task includes an option with an undefined variable. The error was: 'int object' has no attribute 'zfill'
}
So, how can I call python inside the for loop in order to manipulate the information to print with Python instead than Ansible?
Note: I want to call python directly in the loop and I don't want to define variable in python and substitute them into the body of the mail.
the task of my playbook:
- name: Sending e-mail report
community.general.mail:
host: myhost
port: 25
sender: mymail
to:
- [email protected]
subject: "mail of day {{ current_date }}"
subtype: html
body: |
<br>title
<br>text
{% for host in mylist %}
myhost-{{ 'd' % hostvars[host]['number']|int }}
<br>
{% endfor %}
<br>text
<br>closure
CodePudding user response:
SOLVED
Since the first time the error was raised by the use of bulit-in python str()
function , while other elements of python syntax did not raise any error, I guessed python built-in functions cannot be interpreted by Ansible (still I don't understand why).
So I looked up for a way to do the data manipulation by using some python methods of the object, instead than a python function.
So instead of turning the int object into a string with str(my_object)
, I exploited the int python method .__str__()
.
So I substituted the upper line with
myhost-{{ hostvars[host].number.__str__().zfill(3) }}
and this time it worked.
Conclusion
This makes me think one cannot use python functions inside ansible {{ }}
tags, but only python objects methods.