Forum Discussion

vkrishna91's avatar
vkrishna91
Icon for Nimbostratus rankNimbostratus
Oct 10, 2022

Unable to use ansible playbook to upgrade BIGIP - VE to 15.1.6.1 from 15.1.5.1

Hi Team,

I'm trying to utilize ansible playbook to automate our F5 upgrade.
Current version: 15.1.5.1
New version: 15.1.6.1

I'm trying to utilize a bash script to dynamically identify the partition, create the partition if not available and install image and reboot. 
It looks like the bash script doesn't seem to work via ansible but works directly on the F5. 

bash script:

#!/bin/bash
OLDIFS="$IFS"
IFS=$'\n'
disk=$(/bin/tmsh show sys sof status | awk '/.D[1-9]/{print substr($1,1,4)}' | head -n1)
maxvnumber=0

for vnumber in $(/bin/tmsh show sys sof status | grep complete)
do

vnumber=${vnumber:4:2}
vnumber=${vnumber// /}

if (( vnumber > maxvnumber )); then
maxvnumber=$vnumber
fi
done

volume=$disk$((maxvnumber + 3))
echo -n $volume
IFS="$OLDIFS"


I have tried to use tmsh and /bin/tmsh - both seems to fail:
 "vol": {
        "changed": true,
        "failed": false,
        "rc": 0,
        "stderr": "/home/user/.ansible/tmp/ansible-local-61301srclvb76/ansible-tmp-1665415837.2614715-24184-40420301589164/cal_vol.sh: line 4: tmsh: command not found\n/home/user/.ansible/tmp/ansible-local-61301srclvb76/ansible-tmp-1665415837.2614715-24184-40420301589164/cal_vol.sh: line 16: tmsh: command not found\n",
        "stderr_lines": [
            "/home/user/.ansible/tmp/ansible-local-61301srclvb76/ansible-tmp-1665415837.2614715-24184-40420301589164/cal_vol.sh: line 4: tmsh: command not found",
            "/home/user/.ansible/tmp/ansible-local-61301srclvb76/ansible-tmp-1665415837.2614715-24184-40420301589164/cal_vol.sh: line 16: tmsh: command not found"
        ],
        "stdout": "3",
        "stdout_lines": [
            "3"
        ]
    }
}

I have tried to use the root account to login and still seem to throw the same error:

- name: Upload image
bigip_software_image:
provider: "{{ f5_provider }}"
image: "{{ new_image_dir }}/{{ new_image }}"

- name: Get available volume number to use
script: cal_vol.sh
register: vol
- debug:
var: vol

- name: Install Image and reboot
bigip_software_install:
provider: "{{ f5_provider }}"
image: "{{ new_image }}"
state: activated
volume: "HD1.{{ vol.stdout }}"
async: 45
poll: 0
any_errors_fatal: true

when: wants_upgrade

- name: Group 1 Upgrades
block:

- ansible.builtin.import_tasks: checks.yaml
vars:
stage: "pre"
when: check_virts or check_pools or check_ver

- name: Pausing execution to give device time to reboot (first time)
pause:
minutes: 10
when: wants_upgrade

- name: wait for ssh to come up
wait_for_connection:
connect_timeout: 120
sleep: 5
delay: 5
timeout: 300
when: wants_upgrade

Could someone assist us to resolve the issue?
We have close to 200 F5s, would not prefer to upgrade them manually. 




  • Just for anyone else who read this, the issue was a local execution 

     

      connection: local
    

     

    this causes the system to SSH to itself and there is no tmsh on the ansible host.   removing this line and then adding delegate_to: localhost when calling a BIG-IP module solved this issue.  it allows the playbook to remote execute the code via SSH

     

    After removing it and fixing a few code tweaks we were able to launch the code 

  • Yes, 

    "vol": {
    "changed": true,
    "failed": false,
    "rc": 0,
    "stderr": "/home/user/.ansible/tmp/ansible-local-18214oqtdof3x/ansible-tmp-1666017684.1469197-18403-149947201118463/cal_vol.sh: line 4: tmsh: command not found\n/home/user/.ansible/tmp/ansible-local-18214oqtdof3x/ansible-tmp-1666017684.1469197-18403-149947201118463/cal_vol.sh: line 16: tmsh: command not found\n",
    "stderr_lines": [
    "/home/user/.ansible/tmp/ansible-local-18214oqtdof3x/ansible-tmp-1666017684.1469197-18403-149947201118463/cal_vol.sh: line 4: tmsh: command not found",
    "/home/user/.ansible/tmp/ansible-local-18214oqtdof3x/ansible-tmp-1666017684.1469197-18403-149947201118463/cal_vol.sh: line 16: tmsh: command not found"
    ],
    "stdout": "2",
    "stdout_lines": [
    "2"
    ]
    }
    }

    The script doesn't seem to run and it provides an output of value 2 which seem not valid. 

    • Matt_Mabis's avatar
      Matt_Mabis
      Icon for Employee rankEmployee

      Can you post your entire playbook or attach as a file so i can see the code all the way (if you want to show code banks like what i have done above, use the the ICON that looks like </> Change the language to YAML and paste your code and submit that will make it nice and aligned for me to examine 🙂

      Or attach as file

       

       

      • vkrishna91's avatar
        vkrishna91
        Icon for Nimbostratus rankNimbostratus

         

         

         

        ---
        - name: Apply F5 base configs
          hosts: bigip-*
          connection: local
          gather_facts: no
        
          vars:
            netbox_token: "{{ lookup('env', 'NETBOX_TOKEN') }}"
            netbox_host: "{{ lookup('env', 'NETBOX_HOST') | default('https://URL.net/', True) }}"
            f5_provider:
              server: "{{ primary_ip4 }}"
              user: "{{ ansible_user }}"
              password: "{{ ansible_ssh_pass }}"
              validate_certs: False
            
            new_image: "BIGIP-15.1.6.1-0.0.10.iso"
            ## Where on the local system the ISO can be found
            new_image_dir: "image_f5"
            ## Where on the local system to place backups. 
            ## Subdirectories will be created based on the inventory hostname
            backup_loc: "/var/tmp"
            ## Prefix for the backups. For example a change reference, or just "backup".
            ## "pre-upgrade" and "post-upgrade" will be appended to the prefix.
            backup_pfx: "bigip_backup_config"
            
          tasks:
        
            - name: Get available volume number to use
              ansible.builtin.script: "{{ playbook_dir }}/cal_vol.sh"
              register: vol
        
            - debug:
                var: vol
        
            - name: Checking device reachablity
              wait_for: "host={{ inventory_hostname }} port=443 timeout=3"
              check_mode: no
        
            - name: Test auth
              run_once: true
              bigip_device_info:
                gather_subset:
                  - system-info
                provider: "{{ f5_provider }}"
              delegate_to: localhost
        
            - name: Get Software Volume Information
              f5networks.f5_modules.bigip_device_info:
                gather_subset:
                  - software-volumes
                provider: "{{ f5_provider }}"
              register: sv
            
            - name: Get Current Version
              set_fact:
                current_version: "{{ item.version }}"
                current_boot_loc: "{{ item.name }}"
              when: item.active == "yes"
              with_items: "{{ sv.software_volumes }}"
            
            - name: Identify Hosts That Require Upgrade
              set_fact:
                wants_upgrade: True
              when: not new_image.split("-")[1] == current_version
            
            - name: Identify Hosts That Don't Require Upgrade
              set_fact:
                wants_upgrade: False
              when: new_image.split("-")[1] == current_version
              
            - name: Only Upgrading Devices Which Need It
              block:
        
              - name: Check For Only One Boot Location
                set_fact:
                  dest_boot_loc: "{{vol.stdout}}"
                when: (not dest_boot_loc is defined) and (sv.software_volumes|length == 1)
        
              - name: Check First Boot Location
                set_fact:
                  dest_boot_loc: "{{ sv.software_volumes.0.name }}"
                when: (not dest_boot_loc is defined) and (sv.software_volumes.0.active != "yes")
        
              - name: Check Second Boot Location
                set_fact:
                  dest_boot_loc: "{{ sv.software_volumes.1.name }}"
                when: (not dest_boot_loc is defined) and (sv.software_volumes.1.active != "yes")
              
              when: wants_upgrade
        
            - name: Device Version Status
              debug:
                msg:
                  - "Current version: {{ current_version }}"
                  - "Desired image: {{ new_image }}"
                  - "Upgrade needed: {{ wants_upgrade }}"
        
            - name: Print Upgrade Information
              debug:
                msg:
                  - "Current version: {{ current_version }} booting from {{ current_boot_loc }}"
                  - "New Image '{{ new_image }}' will be uploaded from '{{ new_image_dir }}'"
                  - "It will be installed to boot location {{ dest_boot_loc }}"
              when: wants_upgrade
        
            - name: Wait For Confirmation
              pause:
                prompt: "Press a key to continue..."
        
            - name: Save the running configuration of the BIG-IP
              f5networks.f5_modules.bigip_config:
                provider: "{{ f5_provider }}"
                save: yes
              when: wants_upgrade
        
          
            - name: Ensure backup directory exists
              file:
                path: "{{ backup_loc }}/{{ inventory_hostname_short }}"
                state: directory
         
            - name: Get Pre-Upgrade UCS Backup
              f5networks.f5_modules.bigip_ucs_fetch:
                create_on_missing: yes
                src: "{{ backup_pfx }}_pre-upgrade.ucs"
                dest: "{{ backup_loc }}/{{ inventory_hostname_short }}/{{ backup_pfx }}_pre-upgrade.ucs"
                provider: "{{ f5_provider }}"
              when: wants_upgrade
        
            - name: Upload image
              f5networks.f5_modules.bigip_software_image:
                provider: "{{ f5_provider }}"
                image: "{{ new_image_dir }}/{{ new_image }}"
              when: wants_upgrade
             
        
            - name: Activate Image (Will Cause Reboot)
              f5networks.f5_modules.bigip_software_install:
                provider: "{{ f5_provider }}"
                image: "{{ new_image }}"
                state: activated
                volume: "{{ vol.stdout }}"
              when: wants_upgrade
        
        
            - name: Wait for all devices to be healthy before proceeding
              f5networks.f5_modules.bigip_command:
                provider: "{{ f5_provider }}"
                match: "any"
                warn: no
                commands:
                  - bash -c "cat /var/prompt/ps1"
                wait_for:
                  - result[0] contains Active
                  - result[0] contains Standby
                retries: 12
                interval: 10
              register: result
              any_errors_fatal: true
              when: wants_upgrade