I have this task in my playbook:
- name: Update instance tags
command: oci compute instance update -c {{ compartment }} --freeform-tags {{ tag_var_json }}
According to the oracle documentation for this command, the parameter --freeform-tags
accepts a json that represents the key-value pair for the tag. I need to have this json be created dynamically in the playbook itself, so prior to running that task, I have this one for testing purposes:
- name: Create a json object to use as tag
set_fact:
tag_var: '{ "test": "thisisatest" }'
set_fact:
tag_var_json: "{{ tag_var | to_json }}"
But I must be doing something wrong because I keep getting this error:
fatal: [localhost]: FAILED! => {"msg": "The task includes an option with an undefined variable. The error was: 'tag_var' is undefined
Is there an easier way of creating a json directly in the playbook and passing it as an argument to that parameter?
Thank you.
There are two things going on here. The first is that you have created YAML that is accepted by the parser, but behaves in a slightly unexpected way (and will produce a warning in the current version of Ansible.)
Keys in YAML are unique; when the parser encounters a second instance of the same key it throws away the first one. Since you've repeated
set_fact
, this is equivalent to:Correcting the syntax error will still result in a failure, however.
The arguments to
set_fact
have to be templated before the task runs, at which point tag_var is still undefined (because this task is defining it.)One correct way to write this task is as two separate tasks:
However,
set_fact
isn't required at all. You can just set the var directly on the task where you use it, which is both more efficient and makes it more tightly scoped.