Ansible Script Module Not Interpreting Variable - ansible

I am having an issue with the Ansible script module interpreting a with_items variable.
vsa_deploy_config/tasks/main.yml:
- name: Create VSA scripts for center
template:
src: vsa_deploy.ps1.j2
dest: "/opt/ansible/roles/vsa_deploy_config/files/{{ item.vsa_hostname }}.ps1"
when: target == "local"
with_items:
- "{{ vsa_center }}"
- name: Deploy VSAs on Center
script: "files/{{ item.vsa_hostname }}.ps1"
register: out
when: target == "win_center"
- debug: var=out
with_items:
- "{{ vsa_center }}"
vsa_deploy_config/vars/main.yml:
---
vsa_center:
- vcsa_hostname: 10.10.10.74
vcsa_username: administrator#vsphere.local
vcsa_password: password
vcsa_datacenter: DataCenter1
vsa_rdm_lun: 02000000006006bf1d58d25a1020d292f8fcfb22b3554353432d4d
vsa_hostname: sm01-ct01
vsa_mgmt_ip: 10.10.10.75
vsa_mgmt_netmask: 255.255.255.192
vsa_mgmt_gw: 10.10.10.65
vsa_mgmt_ns: 10.10.10.92
vsa_mgmt_pg: SC-MGMT
vsa_mgmt_moref: Network:network-13
vsa_iscsi_ip: 192.168.2.1
vsa_iscsi_netmask: 255.255.255.0
vsa_iscsi_pg: ISCSI
vsa_iscsi_moref: Network:network-22
vsa_mirror_ip: 192.168.5.1
vsa_mirror_netmask: 255.255.255.0
vsa_mirror_pg: Mirror
vsa_mirror_moref: Network:network-23
esxi_hostname: 10.10.10.72
esxi_datastore: DS-01
- vcsa_hostname: 10.10.10.74
vcsa_username: administrator#vsphere.local
vcsa_password: password
vcsa_datacenter: DataCenter1
vsa_rdm_lun: 02000000006006bf1d58d25dd0210bb356a78344e5554353432d4d
vsa_hostname: sm02-ct01
vsa_mgmt_ip: 10.10.10.76
vsa_mgmt_netmask: 255.255.255.192
vsa_mgmt_gw: 10.10.10.65
vsa_mgmt_ns: 10.10.10.92
vsa_mgmt_pg: SC-MGMT
vsa_mgmt_moref: Network:network-13
vsa_iscsi_ip: 192.168.2.2
vsa_iscsi_netmask: 255.255.255.0
vsa_iscsi_pg: ISCSI
vsa_iscsi_moref: Network:network-22
vsa_mirror_ip: 192.168.5.2
vsa_mirror_netmask: 255.255.255.0
vsa_mirror_pg: Mirror
vsa_mirror_moref: Network:network-23
esxi_hostname: 10.2.120.73
esxi_datastore: DS-02
When I run the playbook I get the following error:
TASK [vsa_deploy_config : Deploy VSAs on Center] *******************************************************************************
fatal: [auto-win1.lab.com]: FAILED! => {"failed": true, "msg": "the field 'args' has an invalid value, which appears to include a variable that is undefined. The error was: 'item' is undefined\n\nThe error appears to have been in '/opt/ansible/roles/vsa_deploy_config/tasks/main.yml': line 10, column 3, but may\nbe elsewhere in the file depending on the exact syntax problem.\n\nThe offending line appears to be:\n\n\n- name: Deploy VSAs on Center\n ^ here\n"}
to retry, use: --limit #/opt/ansible/powershell.retry
The first task using the template module interprets the item.vsa_hostname variable correctly, but the script module does not. Is the script module not capable of using with_items?

There is no with_items for your script task:
- name: Deploy VSAs on Center # -\
script: "files/{{ item.vsa_hostname }}.ps1" # \
register: out # / This is task1
when: target == "win_center" # -/
- debug: var=out # -\
with_items: # > This is task2
- "{{ vsa_center }}" # -/
I guess you'd want to move debug to the very bottom:
- name: Deploy VSAs on Center
script: "files/{{ item.vsa_hostname }}.ps1"
register: out
when: target == "win_center"
with_items: "{{ vsa_center }}"
- debug: var=out
P.S. also there is no need to feed unnecessary nested list into with_items.

just move the line - debug: var=out to the end of the file and it will work

Related

use dynamic variable as dictionary name

I have playbook as below:
- name: fetch host group name
set_fact:
group_name: '{{ group_names[0] }}'
- name: get memory and storage minimum requirements
set_fact:
min_memory: "{{ group_name.memory }}"
min_storage: "{{ group_name.storage }}"
In defaults/main.yml
#memory and storage settings
primary:
memory: 32
storage: 128
my inventory host is in primary group.
when I run playbook, I am seeing below error.
TASK [ansible-elastic-cloud-enterprise : get memory and storage minimum requirements] ****************************************************************************************************************************
fatal: [192.168.153.5]: FAILED! => {"msg": "The task includes an option with an undefined variable. The error was: 'str object' has no attribute 'memory'\n\nThe error appears to be in '/cygdrive/c/Users/test/Downloads/ansible-elastic-cloud-enterprise-master/roles/ansible-elastic-cloud-enterprise/tasks/base/general/checkmemorystorage.yml': line 7, column 3, but may\nbe elsewhere in the file depending on the exact syntax problem.\n\nThe offending line appears to be:\n\n\n- name: get memory and storage minimum requirements\n ^ here\n"}
you want to use the content of variable like another variable, so use lookup vars:
sample:
- name: dynamic var
hosts: localhost
gather_facts: no
vars:
groupname: ["primary", "secondary"]
primary:
memory: 32
storage: 128
tasks:
- set_fact:
id: "{{ lookup('vars', groupname[0]) }}"
- debug: msg="{{ id.memory }} -- {{ id.storage }} "
result:
ok: [localhost] => {
"msg": "32 -- 128 "
in your case you should write:
- name: fetch host group name
set_fact:
group_name: '{{ lookup("vars", group_names[0] }}'

azure-network_interface says variable is undefined

We switched to ansible 2.10
Before it was azure_rm_networkinterface_facts (working) now is azure_rm_networkinterface_info
- name: "Get facts for network interface by it's name"
azure_rm_networkinterface_facts:
resource_group: "{{ target_resourcegroup }}"
name: "{{ target_nic_name }}"
- name: "Define private IP address"
set_fact:
private_ip_address: "{{ ansible_facts | json_query(query) }}"
vars:
query: "azure_networkinterfaces[0].properties.ipConfigurations[0].properties.privateIPAddress"
when: azure_networkinterfaces|length > 0
Error I get is:
4 TASK [azure_preconditions : Define private IP address] *************************
00:01:38.844 [0;31mfatal: [40.118.86.58]: FAILED! => {"msg": "The conditional check 'azure_networkinterfaces|length > 0' failed. The error was: error while evaluating conditional (azure_networkinterfaces|length > 0): 'azure_networkinterfaces' is undefined\n\nThe error appears to be in '/var/lib/jenkins/workspace/PA-28544-ansible-version-upgrade/roles/azure_preconditions/tasks/main.yml': line 143, column 3, but may\nbe elsewhere in the file depending on the exact syntax problem.\n\nThe offending line appears to be:\n\n\n- name: \"Define private IP address\"\n ^ here\n"}[0m
00:01:38.844
azure_networkinterfaces seems to be a return value of azure_rm_networkinterface_facts so it's normal that it doesn't exist...
I'd write a playbook like this:
- name: "Get facts for network interface by it's name"
azure_rm_networkinterface_facts:
resource_group: "{{ target_resourcegroup }}"
name: "{{ target_nic_name }}"
register: output
I suggest you debug the output variable to check your return values. I don't know the version of Azure you are using and a lot of changes can exist depending on it.
- name: "Display return value"
debug:
msg: "{{ output }}"
You could play with output.azure_networkinterfaces or output.networkinterfaces
Following the last documentation, its seems azure_rm_networkinterface_fact is deprecated, replaced by azure_rm_networkinterface_info
azure_rm_networkinterface_info

Ansible - set_fact syntax issue

In the below playbook, can someone please tell me what is wrong with the syntax of the final set_fact statement. If i explicitly specify the hostname R9 (as per the first set_fact), then it works without issue. But if I assign a variable to have a value of R9, and then use this in the final set_fact statement, I get the error shown below. Argh.
---
- hosts: all
gather_facts: no
vars:
ansible_network_os: ios
ansible_connection: network_cli
tasks:
- ios_command:
commands: show ip arp
register: results
- set_fact:
some_var: "{{ hostvars['R9'].results }}"
- set_fact:
hostname: "R9"
- set_fact:
another_var: "{{ hostvars['{{hostname}}'].results }}"
- debug:
var=some_var
- debug:
var=another_var
Error:
fatal: [R7]: FAILED! =>
msg: |-
The task includes an option with an undefined variable. The error was: "hostvars['{{hostname}}']" is undefined
The error appears to be in '/root/ansible/Rapid/testsetfact.yml': line 20, column 6, but may
be elsewhere in the file depending on the exact syntax problem.
The offending line appears to be:
- set_fact:
^ here
fatal: [R9]: FAILED! =>
msg: |-
The task includes an option with an undefined variable. The error was: "hostvars['{{hostname}}']" is undefined
The error appears to be in '/root/ansible/Rapid/testsetfact.yml': line 20, column 6, but may
be elsewhere in the file depending on the exact syntax problem.
The offending line appears to be:
- set_fact:
^ here
you can use the inventory_hostname for your purpose:
- set_fact:
another_var: "{{ hostvars[inventory_hostname].results }}"

Syntax to pass dynamic variables to include_tasks along with with_item in Ansible playbook

Executing parent.yml which in turn calls child.yml playbook for execution with dynamic variables.
Variables from parent.yml aren`t interpolated inside child.yml playbook. Correct me if I am using correct syntax?
Parent.yml
- name: Main playbook to call MySQL backup
hosts: localhost
gather_facts: no
tasks:
- include_task: child.yml
vars:
var1: "{{ item.name }}"
var2: "{{ item.db_name }}"
with_items:
- { name: '10.10.10.01', db_name: 'prod1' }
- { name: '10.10.10.02', db_name: 'prod2' }
child.yml (Takes mysqldump from managed DB)
- name: MySQL dump
hosts: localhost
#gather_facts: no
#vars:
# v1: "{{ var1 }}"
# v2: "{{ var2 }}"
tasks:
- name: Executing the shell script
shell: 'mysqldump -h "{{ var1 }}" -u"ansi" -p"*****" "{{ var2 }}"| gzip > /tmp/mysql_dump/"{{ var2 }}"_`date +%Y%m%d-%H%M`.gz'
fatal: [127.0.0.1]: FAILED! => {"reason": "no action detected in task. This often indicates a misspelled module name, or incorrect module path.\n\nThe error appears to be in '/home/ansible/playbooks/DBpatch/Linux/child.yml': line 1, column 3, but may\nbe elsewhere in the file depending on the exact syntax problem.\n\nThe offending line appears to be:\n\n\n- name: MySQL dump\n ^ here\n"}
include_task expects a list of tasks but you give it a complete playbook.
Child.yml should only contain what is currently below the line "tasks:".
See also https://docs.ansible.com/ansible/latest/user_guide/playbooks_reuse_includes.html

The error was: 'dict object' has no attribute 'ansible_facts

I am iterating over yml file and filtering and keeping those microservice metadata in the list which is in the command line argument passed
ansible-playbook -i inventory/inventory sp-deployer.yml --ask-vault-pass --extra-vars '{"microservices_list":[iwan,csrservice]}'
Finally I need these three value from the yml file based on the criteria mentioned above. I have created ansible sp-deployer.yml for this purpose. I have used set_facts for creating dynamic list. First list works fine but the moment I create second one it fails.
name: "ms_service"
port: "830"
streams: "noti,jk-noti"
vars.yml
version: 1
name: user
jobs:
ns1:
ip: "1.1.1.1"
ns_version: "4.2"
f_packs:
- f-pack-1:
name: "pack1"
microservices:
- microservice-1:
name: "ms_service"
port: "830"
streams: "noti,jk-noti"
- microservice-2:
name: "ms_service1"
port: "830"
streams: "noti1,jk-noti1"
- f-pack-2:
name: "pack4"
microservices:
- microservice-1:
name: "ms_service3"
port: "830"
streams: "noti,jk-noti3"
- microservice-2:
name: "ms_service4"
port: "830"
streams: "noti,jk-noti4"
- microservice-3:
name: "ms_service5"
port: "830"
streams: "noti,jk-noti5"
Script:sp-deployer.yml
---
- hosts: localhost
vars_files:
- ./vars.yml
sudo: yes
tasks:
- name: Reading vars.yml file and preparing list of microservice with its metadata
set_fact: foo_item="{{ item.1 }}"
register: result
with_subelements:
- "{{ jobs.ns1.f_packs }}" ###item.0
- microservices ###item.1
- name: make first list
set_fact: foo="{{ result.results | map(attribute='ansible_facts.foo_item') | list }}"
- name: print register
debug: msg="{{ item }}" verbosity=3
with_items:
- "{{ foo }}"
- name: Filtering micro service list with match found from command line input
when: item[0].name == item[1]
set_fact: foo_item1="{{ item.0 }}"
register: result_final
with_nested:
- "{{ foo }}"
- "{{ microservices_list }}"
- name: make a list
set_fact: foo1="{{ result_final.results | map(attribute='ansible_facts.foo_item1') | list }}"
ERROR
TASK [make a list] *************************************************************
fatal: [localhost]: FAILED! => {"failed": true, "msg": "the field 'args' has an invalid value, which appears to include a variable that is undefined. The error was: 'dict object' has no attribute 'ansible_facts'\n\nThe error appears to have been in '/home/user/ansible/sp-deployer1.yml': line 40, column 5, but may\nbe elsewhere in the file depending on the exact syntax problem.\n\nThe offending line appears to be:\n\n\n - name: make a list\n ^ here\n"}
to retry, use: --limit #/home/user/ansible/sp-deployer1.retry
PLAY RECAP *********************************************************************
localhost : ok=4 changed=0 unreachable=0 failed=1
Friendly advice: always check registered variables with debug if you bump on such errors.
The reason for your error is that set_fact don't yield ansible_facts dict if the loop iteration is skipped.
And I see you have when statement in your loop.
To overcome this error, you should select only those loop iterations, that have ansible_facts dict defined:
- name: make a list
set_fact: foo1="{{ result_final.results | selectattr('ansible_facts','defined') | map(attribute='ansible_facts.foo_item1') | list }}"

Resources