Interesting Uses of Ansible's ternary filter
zufallsheld.de
zufallsheld.de
My first love in this space was Chef, and honestly it remains my favorite in config management because you can write things in it that look very non-programmy, but you're still just writing in pure ruby. Obviously Ansible has the advantage being agentless, but I just cannot stand how popular it is.
But yes, trying to work with even mildly complex data structures in Ansible is a nightmare compared to raw Python.
Not that this is good or bad, but I think that's why Ansible took off with the traditional operations-teams.
You don't get that with programming languages. People do all kinds of shit with programming languages. There's tons of good ways to tackle a problem. And exponentially many more bad ways to tackle a problem.
Having a given repeated form makes interpreting & understanding Ansible far easier than the alternatives.
By using yaml ansible basically forces you to be purely declarative, which I found to be a boon, especially once other engineers who similarly didn't initially get the declarative paradigm started on working in the codebase.
Kidding aside, it is somewhat amusing to see the same discussion as when chef happened repeat itself.
Ansible clearly had to take a lot of liberties with the yaml format to make it work in practice. The amount of yaml in yaml you have to write is surprising. I cannot wait for the cycle to repeat itself.
and yet, completely facepalmed by invoking Jinja2 with its default begin and end characters that are meaningful to yaml, thus ensuring billions of person-years of SO questions due to having to quote, sometimes multiple ways, every jinja2 invocation
Contrast that to GitHub Actions which uses ${{ }} for its parameterization and thus no quoting required, in contrast to
- debug:
msg: '{{ "what kind of lack of forethought was this nonsense" }}'Also, don't forget that yaml is way easier to pick up by non-python developers and people unfamiliar with programming.
{{ "--quiet" if ansible_verbosity == 0 }}
https://jinja.palletsprojects.com/en/3.1.x/templates/#if-exp...Thanks, I updated the blog-post.
Also reminds me again that yaml should have never been born. Look how unnatural this "language" is in this article's examples
In a similar mood, I wished Kubernetes was staying every from yaml. Even mentioned HCL would be better (although it's not perfect)
I tried an experiment last year: What if Ansible had Python rather than YAML syntax. https://github.com/linsomniac/uplaybook?tab=readme-ov-file#s...
The downside is that having full Python available makes it really easy to make your playbooks non-idempotent, which Ansible gate-keeps behind Ansible modules. Also someone raised a concern that full Python (rather than a more limited safe dialect like Starlark) would make it harder to trust third-party playbooks. But considering uPlaybook's use case (ansible-like system configuration) it feels like even with a restricted dialect it is going to have plenty of opportunity for nefarious purposes.
I've put out uPlaybook for some limited review among my friends, and I've gotten some excitement about it. It doesn't have fleet management and remote running though, which is the big negative feedback I've gotten. I'm interested in thoughts on it though.
aws_tags_pio: RoleImage: "pio"
aws_tags_role_app_tpl: [ { Role: "app" }, "{{ (mageops_pio_worker_enable and not mageops_pio_worker_dedicated_asg) | ternary(aws_tags_pio, {}) }}" ]
aws_tags_role_app: "{{ aws_tags_role_app_tpl | combine }}"
https://github.com/mageops/ansible-infrastructure/blob/5dcc3...
for array you use flatten eg
aws_security_group_persistant_rules_tpl: [ "{{ mageops_ssh_proxy_persistant | ternary(aws_security_group_persistant_rules_ssh_proxy, []) }}", "{{ mageops_tinyproxy_persistant_enabled | ternary(aws_security_group_persistent_rules_tinyproxy, []) }}" ]
aws_security_group_persistant_rules: "{{ aws_security_group_persistant_rules_tpl | flatten }}"
this pattern really helped to clean up conditionals that normally had to be done in tasks
Everything else should just be handled by a python script to orchestrate the playbooks.