ansible play fails with error - The task includes an option with an undefined variable

212 Views Asked by At

The below ansible code fails with the error: The task includes an option with an undefined variable. The error was: 'storage_size_gb' is undefined

- debug:
    msg: "{{ mongo_output_withoutvar.stdout }}"

- set_fact:
   storage_size_gb: "{{ mongo_output_withoutvar.stdout | int }}"
   min_free_space_rec: "{{ min_free_space_pass | int }}"
   combined_output: "{{ storage_size_gb + min_free_space_rec }} GB"

Output:

TASK [debug] *******************************************************************
ok: [ip-10-236-75-137.ec2.internal] => {
    "msg": "25"
}

TASK [set_fact] ****************************************************************
fatal: [remotehostl]: FAILED! => {"msg": "The task includes an option with an undefined variable. The error was: 'storage_size_gb' is undefined\\n\\nThe error appears to be in '/runner/project/backupmongodb.yml': line 220, column 7, but may\\nbe elsewhere in the file depending on the exact syntax problem.\\n\\nThe offending line appears to be:\\n\\n\\n    - set_fact:\\n      ^ here\\n"}

I tried to run a sample testcase where i get the same error:

---
- hosts: localhost
  gather_facts: false

  vars:
    min_free_space_pass: "30"

  tasks:
    - set_fact:
        storage_size_gb: 40
        min_free_space_rec: "{{ min_free_space_pass | int }}"
        combined_output: "{{ storage_size_gb + min_free_space_rec }} GB"

    - debug:
        var: combined_output

Run: ansible-playbook sample.yml

Output:

PLAY [localhost] ************************************************************************************************************** 

TASK [set_fact] ***************************************************************************************************************

Wednesday 11 October 2023  02:41:29 -0500 (0:00:00.055)       0:00:00.055 *****

fatal: [localhost]: FAILED! => {"msg": "The task includes an option with an undefined variable. The error was: 'storage_size_gb' is undefined\n\nThe error appears to be in '/home/wladmin/testset.yml': line 7, column 7, but may\nbe elsewhere in the file depending on the exact syntax problem.\n\nThe offending line appears to be:\n\n  tasks:\n    - set_fact:\n      ^ here\n"}

PLAY RECAP ********************************************************************************************************************

localhost                  : ok=0    changed=0    unreachable=0    failed=1    skipped=0    rescued=0    ignored=0

Can you please suggest how I can overcome this error?

1

There are 1 best solutions below

0
Zeitounator On BEST ANSWER

The error comes from the fact you declare and use the same variable inside the same set_fact task as reported in @β.εηοιτ.βε comment. Meanwhile, there is absolutely no valid reason to use set_fact here. The following playbook should get you going:

---
- hosts: localhost
  gather_facts: false

  vars:
    min_free_space_pass: 30
    storage_size_gb: 40
    combined_output: "{{ storage_size_gb | int + min_free_space_pass | int }} GB"

  tasks:
    - ansible.builtin.debug:
        var: combined_output

Running the playbook gives:

$ ansible-playbook test_playbook.yml

PLAY [localhost] ***************************************************************

TASK [debug] *******************************************************************
ok: [localhost] => {
    "combined_output": "70 GB"
}

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

To apply this to your real case (where I suspect you register a value from an other task) here is a pseudo example:

---
- hosts: whatever_group
  gather_facts: false

  vars:
    min_free_space_pass: 30
    combined_output: "{{ mongo_output_withoutvar.stdout | int + min_free_space_pass | int }} GB"

  tasks:
    - name: Get info from mongo (dummy task to replace with real)
      ansible.builtin.command: echo 40
      register: mongo_output_withoutvar
      changed_when: false

    - name: Debug my var
      ansible.builtin.debug:
        var: combined_output

This is also testable (targeting only localhost for the test). But note that this will work for whatever number of servers you target:

$ ansible-playbook almost_real_playbook.yml

PLAY [localhost] ***********************************************************************************************************************

TASK [Get info from mongo (dummy task to replace with real)] **************************************************************************
ok: [localhost]

TASK [Debug my var] ********************************************************************************************************************
ok: [localhost] => {
    "combined_output": "70 GB"
}

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