infoblox-ansible
infoblox-ansible copied to clipboard
nios lookup plugin returns different types based on number of results
python 3.8.11 ansible core 2.12.1 wapi_version: "2.10.5"
The nios lookup plugin returns the following when using term 'record:a'
- If no records match, it returns and empty list
- if a single record matches, it returns a dictionary
- if more that one records matches, it returns a list of dictionaries
Returning a list in all three scenarios would be easier to work with in ansible.
Example playbook:
- hosts: test_grid
connection: local
gather_facts: no
vars:
rec_type: "record:a"
host_name:""
domain_name: "net.testdomain.com"
fqdn: "{{host_name}}.{{domain_name}}"
tasks:
- name: use lookup to get a record
set_fact:
host: "{{ lookup('nios', rec_type, filter={'name':fqdn }, provider=nios_provider) }}"
- name: display information about the results
debug:
msg:
- "Variable 'host' has type: '{{ host|type_debug }}'' and length: '{{ host|length }}'"
- "{{ host }}"
Sample playbook runs using host_name = test-rec0, test-rec1 and test-rec2
(iblox) [user@server iblox-ansible]$ ansible-playbook -i inventory get_dns_record.yaml -e host_name=test-rec0
PLAY [test_grid] ***********************************************************************************************************************************************************
TASK [use lookup to get a record] ******************************************************************************************************************************************
ok: [test_grid]
TASK [display information about the results] *******************************************************************************************************************************
ok: [test_grid] => {
"msg": [
"Variable 'host' has type: 'list'' and length: '0'",
[]
]
}
PLAY RECAP *****************************************************************************************************************************************************************
test_grid : ok=2 changed=0 unreachable=0 failed=0 skipped=0 rescued=0 ignored=0
(iblox) [user@server iblox-ansible]$ ansible-playbook -i inventory get_dns_record.yaml -e host_name=test-rec1
PLAY [test_grid] ***********************************************************************************************************************************************************
TASK [use lookup to get a record] ******************************************************************************************************************************************
ok: [test_grid]
TASK [display information about the results] *******************************************************************************************************************************
ok: [test_grid] => {
"msg": [
"Variable 'host' has type: 'dict'' and length: '4'",
{
"_ref": "record:a/ZG5zLmJpbmRfYSQuX2RlZmF1bHQuY29tLnRocml2ZW50Lm5ldCx0ZXN0LXJlYzEsMTAuODAuMjU1Ljc:test-rec1.net.testdomain.com/Internal%20DNS",
"ipv4addr": "10.1.1.7",
"name": "test-rec1.net.testdomain.com",
"view": "Internal DNS"
}
]
}
PLAY RECAP *****************************************************************************************************************************************************************
test_grid : ok=2 changed=0 unreachable=0 failed=0 skipped=0 rescued=0 ignored=0
(iblox) [user@server iblox-ansible]$ ansible-playbook -i inventory get_dns_record.yaml -e host_name=test-rec2
PLAY [test_grid] ***********************************************************************************************************************************************************
TASK [use lookup to get a record] ******************************************************************************************************************************************
ok: [test_grid]
TASK [display information about the results] *******************************************************************************************************************************
ok: [test_grid] => {
"msg": [
"Variable 'host' has type: 'list'' and length: '2'",
[
{
"_ref": "record:a/ZG5zLmJpbmRfYSQuX2RlZmF1bHQuY29tLnRocml2ZW50Lm5ldCx0ZXN0LXJlYzIsMTAuODAuMjU1LjIy:test-rec2.net.testdomain.com/Internal%20DNS",
"ipv4addr": "10.1.1.22",
"name": "test-rec2.net.testdomain.com",
"view": "Internal DNS"
},
{
"_ref": "record:a/ZG5zLmJpbmRfYSQuX2RlZmF1bHQuY29tLnRocml2ZW50Lm5ldCx0ZXN0LXJlYzIsMTAuODAuMjU1LjIz:test-rec2.net.testdomain.com/Internal%20DNS",
"ipv4addr": "10.1.1.23",
"name": "test-rec2.net.testdomain.com",
"view": "Internal DNS"
}
]
]
}
PLAY RECAP *****************************************************************************************************************************************************************
test_grid : ok=2 changed=0 unreachable=0 failed=0 skipped=0 rescued=0 ignored=0
@dwebr I had similar issue dealing with the return json. Here is how I dealt with it. This was written to take a list of IP addresses and return all the records associated to those IP's. But with jmespath you can really do whatever you want with the data. But you will notice that I wrap the response in an array in case it comes back as a object. if there not needed they will get stripped out. Not sure if it's the best way to deal with it but works for me.
# Host Record ipv4 Search
- name: Search Host Records by IP.
set_fact:
hostv4_records: "{{ hostv4_records | default([]) + [ lookup('nios', 'record:host', filter={'ipv4addr': item}, return_fields=['name','view','ipv4addrs.ipv4addr','ipv4addrs.host','ttl','extattrs','ipv6addrs.ipv6addr','ipv6addrs.host'], provider=provider)] }}"
loop: "{{ ip_address }}"
# Host Record ipv6 Search
- name: Search Host Records by IP.
set_fact:
hostv6_records: "{{ hostv6_records | default([]) + [ lookup('nios', 'record:host', filter={'ipv6addr': item}, return_fields=['name','view','ipv6addrs.ipv6addr','ipv4addrs.host','ttl','extattrs','ipv6addrs.ipv6addr','ipv4addrs.host'], provider=provider)] }}"
loop: "{{ ip_address }}"
# A Record Search
- name: Search A Records by IP.
set_fact:
a_records: "{{ a_records | default([]) + [ lookup('nios', 'record:a', filter={'ipv4addr': item}, return_fields=['name','view','ipv4addr','ttl','extattrs'], provider=provider)] }}"
loop: "{{ ip_address }}"
# AAAA Record Search
- name: Search AAAA Records by IP.
set_fact:
aaaa_records: "{{ aaaa_records | default([]) + [ lookup('nios', 'record:aaaa', filter={'ipv6addr': item}, return_fields=['name','view','ipv6addr','ttl','extattrs'], provider=provider)] }}"
loop: "{{ ip_address }}"
- name: Combining search results.
set_fact:
search_results: "{{ search_results | default([]) }} + {{ hostv4_records | json_query(query_host) }} + {{ hostv6_records | json_query(query_host) }} + {{ a_records | json_query(query_a) }} + {{ aaaa_records | json_query(query_aaaa) }}"
vars:
query_host: "[].{name: name, ipv4addrs: ipv4addrs[].ipv4addr, ipv6addrs: ipv6addrs[].ipv6addr, ttl: ttl, type: 'host', view: view}"
query_a: "[].{name: name, ipv4addr: ipv4addr, ttl: ttl, type: 'a', view: view}"
query_aaaa: "[].{name: name, ipv6addr: ipv6addr, ttl: ttl, type: 'aaaa', view: view}"
- name: Printing search results.
debug:
msg: "{{ search_results }}"