python – Ansible seems to be ignoring variable in when conditional when it is overridden with “-e” from the command line

I’m working on an Ansible playbook that uses a when condition, and I was trying to test the scenario where there is a default value specified as a play variable, which can then be selectively overridden from the command line using the -e argument to ansible-playbook. But this is not working as I would expect, and I’m not seeing any obvious reason(s) why.

Here’s the setup (this is a super stripped down sample, just to show the point, not my real playbook).

conditional_task.yml

- name: A playbook to conditionally print some debug messages
  hosts: localhost
  gather_facts: False
  vars:
    doomed: False
  tasks:
    - name: print the value of doomed
      debug: var=doomed
    - name: print the message if we're doomed
      debug:
        msg: "We're fucking doomed!"
      when: doomed == True
    - name: print the message if we're not doomed
      debug:
        msg: "Glory be to FSM, we are saved!"
      when: doomed == False

If I run this with the ansible-playbook command with no arguments, I get exactly the expected output.

$ ansible-playbook conditional_task.yml

PLAY [A playbook to conditionally print some debug messages] ************************************************************************************

TASK [print the value of doomed] ****************************************************************************************************************
ok: [localhost] => {
    "doomed": true
}

TASK [print the message if we're doomed] ********************************************************************************************************
ok: [localhost] => {
    "msg": "We're fucking doomed!"
}

TASK [print the message if we're not doomed] ****************************************************************************************************
skipping: [localhost]

PLAY RECAP **************************************************************************************************************************************
localhost                  : ok=2    changed=0    unreachable=0    failed=0    skipped=1    rescued=0    ignored=0  

And if I edit the playbook to change the value of the doomed var to False, and re-run this, I get the other message.

$ ansible-playbook conditional_task.yml

PLAY [A playbook to conditionally print some debug messages] ************************************************************************************

TASK [print the value of doomed] ****************************************************************************************************************
ok: [localhost] => {
    "doomed": false
}

TASK [print the message if we're doomed] ********************************************************************************************************
skipping: [localhost]

TASK [print the message if we're not doomed] ****************************************************************************************************
ok: [localhost] => {
    "msg": "Glory be to FSM, we are saved!"
}

PLAY RECAP **************************************************************************************************************************************
localhost                  : ok=2    changed=0    unreachable=0    failed=0    skipped=1    rescued=0    ignored=0

Now, given all that, I would expect to be able to do something like this:

$ ansible-playbook -e doomed=False conditional_task.yml

and get the “not doomed” message. What I get instead is this:

$ ansible-playbook -e doomed=False conditional_task.yml

PLAY [A playbook to conditionally print some debug messages] ************************************************************************************

TASK [print the value of doomed] ****************************************************************************************************************
ok: [localhost] => {
    "doomed": false
}

TASK [print the message if we're doomed] ********************************************************************************************************
skipping: [localhost]

TASK [print the message if we're not doomed] ****************************************************************************************************
skipping: [localhost]

PLAY RECAP **************************************************************************************************************************************
localhost                  : ok=1    changed=0    unreachable=0    failed=0    skipped=2    rescued=0    ignored=0

As you can see, neither when condition fires in this case. It’s almost like the variable isn’t there at all, or has some unexpected value, or something. But as the debug output shows, the variable is defined, and does have value “false” as expected. And yet the “when” conditionals ignore this.

It also doesn’t matter if I change the command line to

$ ansible-playbook -e doomed=True conditional_task.yml

In that case I still get neither conditional task executing. But again, the debug statement shows that doomed is present and has value of “true”.

I also tried re-writing my conditions as “doomed is true” and “doomed is false” respectively, instead of using the == operator and that didn’t make any difference. At this point I’m stuck. If anybody can explain this, it would be greatly appreciated.

Here’s my Ansible version information:

$ ansible-playbook --version
ansible-playbook 2.10.8
  config file = /extradrive1/development/experimental/ansible/ansible_experimental/ansible.cfg
  configured module search path = ['/home/prhodes/.ansible/plugins/modules', '/usr/share/ansible/plugins/modules']
  ansible python module location = /usr/lib/python3/dist-packages/ansible
  executable location = /usr/bin/ansible-playbook
  python version = 3.9.7 (default, Sep 10 2021, 14:59:43) [GCC 11.2.0]

This is all running on Pop! OS:

NAME="Pop!_OS"
VERSION="21.10"

Leave a Comment