Exercise 2.0 - Updating the router configurations using Ansible

Using Ansible you can update the configuration of routers either by pushing a configuration file to the device or you can push configuration lines directly to the device.

Step 1

Create a new file called router_configs.yml (use either vim or nano on the jumphost to do this or use a local editor on your laptop and copy the contents to the jumphost later). Add the following play definition to it:

---
- name: SNMP RO/RW STRING CONFIGURATION
  hosts: cisco
  gather_facts: no
  connection: network_cli

Step 2

Add a task to ensure that the SNMP strings ansible-public and ansible-private are present on all the routers. Use the ios_config module for this task

Note: For help on the ios_config module, use the ansible-doc ios_config command from the command line or check docs.ansible.com. This will list all possible options with usage examples.


---
- name: SNMP RO/RW STRING CONFIGURATION
  hosts: cisco
  gather_facts: no
  connection: network_cli

  tasks:

    - name: ENSURE THAT THE DESIRED SNMP STRINGS ARE PRESENT
      ios_config:
        commands:
          - snmp-server community ansible-public RO
          - snmp-server community ansible-private RW

Step 3

Run the playbook:

[student1@ansible networking-workshop]$ ansible-playbook -i lab_inventory/hosts router_configs.yml

PLAY [UPDATE THE SNMP RO/RW STRINGS] ********************************************************************

TASK [ENSURE THAT THE DESIRED SNMP STRINGS ARE PRESENT] *************************************************
changed: [rtr4]
changed: [rtr1]
changed: [rtr3]
changed: [rtr2]

PLAY RECAP **********************************************************************************************
rtr1                       : ok=1    changed=1    unreachable=0    failed=0   
rtr2                       : ok=1    changed=1    unreachable=0    failed=0   
rtr3                       : ok=1    changed=1    unreachable=0    failed=0   
rtr4                       : ok=1    changed=1    unreachable=0    failed=0   

[student1@ansible networking-workshop]$

Feel free to log in and check the configuration update.

Step 4

The ios_config module is idempotent. This means, a configuration change is pushed to the device if and only if that configuration does not exist on the end hosts. To validate this, go ahead and re-run the playbook:

[student1@ansible networking-workshop]$ ansible-playbook -i lab_inventory/hosts router_configs.yml  

PLAY [UPDATE THE SNMP RO/RW STRINGS] ********************************************************************************************************************************************************

TASK [ENSURE THAT THE DESIRED SNMP STRINGS ARE PRESENT] *************************************************************************************************************************************
ok: [rtr1]
ok: [rtr2]
ok: [rtr4]
ok: [rtr3]

PLAY RECAP **********************************************************************************************************************************************************************************
rtr1                       : ok=1    changed=0    unreachable=0    failed=0   
rtr2                       : ok=1    changed=0    unreachable=0    failed=0   
rtr3                       : ok=1    changed=0    unreachable=0    failed=0   
rtr4                       : ok=1    changed=0    unreachable=0    failed=0   

[student1@ansible networking-workshop]$



Note: See that the changed parameter in the PLAY RECAP indicates 0 changes.

Step 5

Now update the task to add one more SNMP RO community string:

---
- name: UPDATE THE SNMP RO/RW STRINGS
  hosts: cisco
  gather_facts: no
  connection: network_cli

  tasks:

    - name: ENSURE THAT THE DESIRED SNMP STRINGS ARE PRESENT
      ios_config:
        commands:
          - snmp-server community ansible-public RO
          - snmp-server community ansible-private RW
          - snmp-server community ansible-test RO

Step 6

This time however, instead of running the playbook to push the change to the device, execute it using the --check flag in combination with the -v or verbose mode flag:

[student1@ansible networking-workshop]$ ansible-playbook -i lab_inventory/hosts router_configs.yml  --check -v
Using /home/student1/.ansible.cfg as config file

PLAY [UPDATE THE SNMP RO/RW STRINGS] ********************************************************************************************************************************************************

TASK [ENSURE THAT THE DESIRED SNMP STRINGS ARE PRESENT] *************************************************************************************************************************************
changed: [rtr3] => {"banners": {}, "changed": true, "commands": ["snmp-server community ansible-test RO"], "updates": ["snmp-server community ansible-test RO"]}
changed: [rtr1] => {"banners": {}, "changed": true, "commands": ["snmp-server community ansible-test RO"], "updates": ["snmp-server community ansible-test RO"]}
changed: [rtr2] => {"banners": {}, "changed": true, "commands": ["snmp-server community ansible-test RO"], "updates": ["snmp-server community ansible-test RO"]}
changed: [rtr4] => {"banners": {}, "changed": true, "commands": ["snmp-server community ansible-test RO"], "updates": ["snmp-server community ansible-test RO"]}

PLAY RECAP **********************************************************************************************************************************************************************************
rtr1                       : ok=1    changed=1    unreachable=0    failed=0   
rtr2                       : ok=1    changed=1    unreachable=0    failed=0   
rtr3                       : ok=1    changed=1    unreachable=0    failed=0   
rtr4                       : ok=1    changed=1    unreachable=0    failed=0   

[student1@ansible networking-workshop]$

The --check mode in combination with the -v flag will display the exact changes that will be deployed to the end device without actually pushing the change. This is a great technique to validate the changes you are about to push to a device before pushing it.

Go ahead and log into a couple of devices to validate that the change has not been pushed.

Also note that even though 3 commands are being sent to the device as part of the task, only the one command that is missing on the devices will be pushed.

Step 7

Finally re-run this playbook again without the -v or --check flag to push the changes.

[student1@ansible networking-workshop]$ ansible-playbook -i lab_inventory/hosts router_configs.yml  

PLAY [UPDATE THE SNMP RO/RW STRINGS] ********************************************************************************************************************************************************

TASK [ENSURE THAT THE DESIRED SNMP STRINGS ARE PRESENT] *************************************************************************************************************************************
changed: [rtr1]
changed: [rtr2]
changed: [rtr4]
changed: [rtr3]

PLAY RECAP **********************************************************************************************************************************************************************************
rtr1                       : ok=1    changed=1    unreachable=0    failed=0   
rtr2                       : ok=1    changed=1    unreachable=0    failed=0   
rtr3                       : ok=1    changed=1    unreachable=0    failed=0   
rtr4                       : ok=1    changed=1    unreachable=0    failed=0   

[student1@ansible networking-workshop]$

Step 8

Rather than push individual lines of configuration, an entire configuration snippet can be pushed to the devices. Create a file called secure_router.cfg in the same directory as your playbook and add the following lines of configuration into it:

line con 0
 exec-timeout 5 0
line vty 0 4
 exec-timeout 5 0
 transport input ssh
ip ssh time-out 60
ip ssh authentication-retries 5
service password-encryption
service tcp-keepalives-in
service tcp-keepalives-out

Step 9

Remember that a playbook contains a list of plays. Add a new play called HARDEN IOS ROUTERS to the router_configs.yml playbook.


---
- name: UPDATE THE SNMP RO/RW STRINGS
  hosts: cisco
  gather_facts: no
  connection: network_cli

  tasks:

    - name: ENSURE THAT THE DESIRED SNMP STRINGS ARE PRESENT
      ios_config:
        commands:
          - snmp-server community ansible-public RO
          - snmp-server community ansible-private RW
          - snmp-server community ansible-test RO


- name: HARDEN IOS ROUTERS
  hosts: cisco
  gather_facts: no
  connection: network_cli



Step 10

Add a task to this new play to push the configurations in the secure_router.cfg file you created in STEP 8

---
- name: UPDATE THE SNMP RO/RW STRINGS
  hosts: cisco
  gather_facts: no
  connection: network_cli

  tasks:

    - name: ENSURE THAT THE DESIRED SNMP STRINGS ARE PRESENT
      ios_config:
        commands:
          - snmp-server community ansible-public RO
          - snmp-server community ansible-private RW
          - snmp-server community ansible-test RO


- name: HARDEN IOS ROUTERS
  hosts: cisco
  gather_facts: no
  connection: network_cli

  tasks:

    - name: ENSURE THAT ROUTERS ARE SECURE
      ios_config:
        src: secure_router.cfg

Step 11

Go ahead and run the playbook.

[student1@ansible networking-workshop]$ ansible-playbook -i lab_inventory/hosts router_configs.yml  

PLAY [UPDATE THE SNMP RO/RW STRINGS] ********************************************************************************************************************************************************

TASK [ENSURE THAT THE DESIRED SNMP STRINGS ARE PRESENT] *************************************************************************************************************************************
ok: [rtr3]
ok: [rtr2]
ok: [rtr1]
ok: [rtr4]

PLAY [HARDEN IOS ROUTERS] *******************************************************************************************************************************************************************

TASK [ENSURE THAT ROUTERS ARE SECURE] *******************************************************************************************************************************************************
changed: [rtr4]
changed: [rtr3]
changed: [rtr2]
changed: [rtr1]

PLAY RECAP **********************************************************************************************************************************************************************************
rtr1                       : ok=2    changed=1    unreachable=0    failed=0   
rtr2                       : ok=2    changed=1    unreachable=0    failed=0   
rtr3                       : ok=2    changed=1    unreachable=0    failed=0   
rtr4                       : ok=2    changed=1    unreachable=0    failed=0   

[student1@ansible networking-workshop]$

Complete

You have completed lab exercise 2.0


Click Here to return to the Ansible Linklight - Networking Workshop