Jason2
(Jason)
June 20, 2020, 3:04am
1
I am working on a project that would require me to bump (shutdown and re-enable) switchports that are connected to an Access Point.
I have created a playbook to run a command “show cdp neighbours” on the switch, and that output would look like:
What I want to do, is to use ansible to only run a command (ansible play) on Gig 1/0/19 in this case. For other switches, it may be more switchports and maybe in different format (eg. Gi 2/0/35).
Is there a way to filter ansible output by looking for ‘AIR-AP280’ and then extract that corresponding Local Interface (switchport number)?
Or if there is another way to get done what I want, then great.
Any suggestions/recommendations?
It is over 50 switches, so it would be great if ansible can do what I want to do.
Jason
(Jason)
June 20, 2020, 3:22am
2
I would use the genie module and run the show cdp neighbor command. Then set fact and use that with the when command.
(attachments)
Jason2
(Jason)
June 20, 2020, 6:34pm
3
Thanks. If you don’t mind me asking because I am not familiar with this, can you give me an example of how to use the set fact and when statement for my case?
Jason
(Jason)
June 22, 2020, 1:05pm
4
Something like that I suppose.
#Sets a varaiable for cdp neighbor detail
name: Run show cdp neighbors command
ios_command:
commands:
show cdp neighbors detail
register: neighbors
Using the Genie Filter Plugin from the Genie Parse Role
Set pyats_neighbors as a dictionary
name: Set fact with Genie Filter Plugin
set_fact:
pyats_neighbors: “{{ neighbors[‘stdout’][0] | clay584.genie.parse_genie(command=‘show cdp neighbors detail’, os=‘ios’) }}”
name: Add interface desription
ios_interfaces:
config:
name: “{{ item.value.local_interface }}”
description: “{{ item.value.device_id }} - {{ item.value.port_id }}”
state: merged
loop: “{{ q(‘dict’, pyats_neighbors.index) }}”
when: item.value.port_id is “AIR-AP280”
Jason2
(Jason)
June 22, 2020, 7:44pm
5
Thanks alot.
I have been getting this error for the past few days when trying to use genie:
fatal: [SW1]: FAILED! => {
“msg”: “template error while templating string: no filter named ‘clay584.genie.parse_genie’. String: {{ neighbors[‘stdout’][0] | clay584.genie.parse_genie(command=‘show cdp neighbors’, os=‘ios’) }}”
}
This is my playbook (what you sent but I needed to import the role first):
hosts: uwioc-switches
gather_facts: no
tasks:
name: Import role
include_role:
name: clay584.parse_genie
name: Run show cdp neighbors
ios_command:
commands:
show cdp neighbors
register: neighbors
Using the Genie Filter Plugin from the Genie Parse Role
Set pyats_neighbors as a dictionary
name: Set fact with Genie
name: Import role
include_role:
name: clay584.parse_genie
name: Run show cdp neighbors
ios_command:
commands:
show cdp neighbors
register: neighbors
Using the Genie Filter Plugin from the Genie Parse Role
Set pyats_neighbors as a dictionary
name: Set fact with Genie Filter Plugin
set_fact:
pyats_neighbors: “{{ neighbors[‘stdout’][0] | clay584.genie.parse_genie(command=‘show cdp neighbors’, os=‘ios’) }}”
name: Add interface description
ios_interfaces:
config:
name: “{{ item.value.local_interface }}”
description: “{{ item.value.device_id }} - {{ item.value.port_id }}”
state: merged
loop: “{{ q(‘dict’, pyats_neighbors.index) }}”
when: item.value.port_id is “AIR-AP280”
My python version is 3.6.8 and Ansible is 2.9.9
I followed this guide to install the necessary libraries:
https://developer.cisco.com/codeexchange/github/repo/clay584/parse_genie/
The error still persists. Also posted the issue on GitHub. Not sure if it is bug in the parsing library.
Any assistance would greatly be appreciated.
Thanks.
Jason
(Jason)
June 22, 2020, 8:15pm
6
I am using the collection not the role. So it looks like this at the top. Had to add the interpreter variable because Ansible kept using Python 2
Jason2
(Jason)
June 22, 2020, 8:48pm
7
This error shows:
fatal: [SW1]: FAILED! => {“msg”: “template error while templating string: no filter named ‘clay584.genie.parse_genie’. String: {{ neighbors[‘stdout’][0] | clay584.genie.parse_genie(command=‘show cdp neighbors’, os=‘ios’) }}”}
This is the full playbook I am using:
Jason
(Jason)
June 23, 2020, 3:21pm
8
Not sure it seems like it is looking for the filter. Have you used a collection before? Is the collections_path defined in the ansible.cfg?
Jason2
(Jason)
June 23, 2020, 3:29pm
9
No I have never used a collection before. So my ansible.cfg is currently to the default
Jason
(Jason)
June 23, 2020, 3:33pm
10
You need to add a new line under [defaults]
collections_paths = /path/to/collections
Jason2
(Jason)
June 23, 2020, 5:30pm
11
I added it. Now this shows:
fatal: [SW1]: FAILED! => {
“msg”: “parse_genie: Genie package is not installed. To install, run ‘pip install genie’.”
}
When I do pip or pip3 install genie, it says requirements already satisfied (as I already installed it).
Just to show you what my directories look like:
And under [defaults] in my ansible.cfg:
collections_paths = /etc/ansible/collections/ansible_collections/
Tried putting a less specific and then a more specifc path to the collections folder also. (= /etc/ansible/collections, = /etc/ansible/collections/ansible_collections/clay584/genie)
Prior to this, I did a ansible-galaxy collection install clay584.genie to install the collection and it said this:
Installing ‘clay584.genie:0.1.11’ to ‘/root/.ansible/collections/ansible_collections/clay584/genie’
Did I do anything wrong?
Jason
(Jason)
June 23, 2020, 6:04pm
12
Well at this point I would probably remove genie. Then create a virtual python environment. Run the pip install commands and see if that works for you. If you are still running into issues I would reach out to the guys who made genie - I think Clay is in the group there too.
https://eurl.io/#r18UzrQVr
(attachments)