Ansible Reboot Check

95 views
Skip to first unread message

Chris Bidwell - NOAA Federal

unread,
Oct 10, 2018, 3:56:23 PM10/10/18
to ansible...@googlegroups.com
Hey all,

take a look at this and lemme know where I'm hosed at.  The errors are a bit misleading:

---
- name: Check who needs reboots
  hosts: ALL_RHEL
  become: yes

  vars_files:
    - passwd.yml
    - vars.yml

  tasks:
    - name: check packages for updates
      shell: yum list updates | awk 'f;/Updated Packages/{f=1;}' | awk '{ print $1 }'
      changed_when: updates.stdout > "0"
      args:
        warn: false
      register: updates

    - name: display count
      debug:
        msg: "Found {{ updates.stdout_lines | length }} packages to be updated:\n\n{{ updates.stdout }}"

    - when: updates.stdout > "0"
      block:
        - name: install updates using yum
          yum:
            name: "*"
            state: latest
          async: 45
          poll: 0

        - name: install yum-utils
          package:
            name: yum-utils

        - name: check if reboot is required RHEL7
          shell: needs-restarting -r
          failed_when: false
          register: reboot_required
          changed_when: false
          when:
            - ansible_os_family == 'RedHat'
            - ansible_distribution_major_version | version_compare('7', '=')

        - name: check if reboot is reqd RHEL6
          shell: LAST_KERNEL=$(rpm -q --last kernel | awk 'NR==1{sub(/kernel-/,""); print $1}'); CURRENT_KERNEL=$(uname -r); if [ $LAST_KERNEL != $CURRENT_KERNEL ]; then echo 'reboot'; else echo 'no'; fi
          failed_when: false
          register: reboot_required
          changed_when: false
          when:
            - ansible_os_family == 'RedHat'
            - ansible_distribution_major_version | version_compare('6', '=')
          

    - when: #(updates.stdout_lines | length > 0 and reboot_required.rc != 0) or
        - reboot_required.stdout == "reboot"
      block:
        - name: reboot the server if required
          shell: sleep 3; reboot
          ignore_errors: true
          changed_when: false
          async: 1
          poll: 0

        - name: wait for server to come back after reboot
          wait_for_connection:
            timeout: 600
            delay: 20
          register: reboot_result

        - name: reboot time
          debug:
            msg: "The system rebooted in {{ reboot_result.elapsed }} seconds."

Here's the part where it dies:  The RHEL6 check doesn't seem to be running like it's supposed to.
Thanks!

TASK [install yum-utils] **********************************************************************************************************************************************
skipping: [baseserver-lx]

TASK [check if reboot is required RHEL7] ******************************************************************************************************************************
skipping: [baseserver-lx]

TASK [check if reboot is reqd RHEL6] **********************************************************************************************************************************
skipping: [baseserver-lx]

TASK [reboot the server if required] **********************************************************************************************************************************
fatal: [baseserver-lx.swpc.noaa.gov]: FAILED! => {"msg": "The conditional check 'reboot_required.stdout == \"reboot\"' failed. The error was: error while evaluating conditional (reboot_required.stdout == \"reboot\"): 'dict object' has no attribute 'stdout'\n\nThe error appears to have been in '/etc/ansible/roles/needs-reboot.yml': line 57, column 11, but may\nbe elsewhere in the file depending on the exact syntax problem.\n\nThe offending line appears to be:\n\n      block:\n        - name: reboot the server if required\n          ^ here\n"}
...ignoring

TASK [wait for server to come back after reboot] **********************************************************************************************************************
fatal: [baseserver-lx]: FAILED! => {"msg": "The conditional check 'reboot_required.stdout == \"reboot\"' failed. The error was: error while evaluating conditional (reboot_required.stdout == \"reboot\"): 'dict object' has no attribute 'stdout'\n\nThe error appears to have been in '/etc/ansible/roles/needs-reboot.yml': line 64, column 11, but may\nbe elsewhere in the file depending on the exact syntax problem.\n\nThe offending line appears to be:\n\n\n        - name: wait for server to come back after reboot\n          ^ here\n"}


Scott Sturdivant

unread,
Oct 10, 2018, 6:13:51 PM10/10/18
to ansible...@googlegroups.com
The 'check if reboot is required' tasks were both skipped, resulting in 'reboot_required' not being defined.

--
You received this message because you are subscribed to the Google Groups "Ansible Project" group.
To unsubscribe from this group and stop receiving emails from it, send an email to ansible-proje...@googlegroups.com.
To post to this group, send email to ansible...@googlegroups.com.
To view this discussion on the web visit https://groups.google.com/d/msgid/ansible-project/CAHKi8CiZWJk8tdGx8u-HC%2Bk-EFgOrXRqPrWGduuJrgeA62CwoA%40mail.gmail.com.
For more options, visit https://groups.google.com/d/optout.

Karl Auer

unread,
Oct 10, 2018, 6:41:04 PM10/10/18
to ansible-project
Yes. One simple cure would be to do an initial set_fact to set reboot_required to false, so that even if neither of the skipped tasks sets it, the variable is there to be checked.

A second simple cure would be to set it to false after the the other tests, conditional upon it not already being defined, so:

   - set fact:
        reboot_required: "{{ reboot_required |default(false) }}"

or

   - set_fact:
        reboot_required: false
     when: reboot_required is undefined

BTW both of those are off the top of my head so probably syntactically wrong but you get the idea :-)

A slightly less simple cure would be to check whether it is defined as part of the test of its value. much as you have done with stdout length. I think is be less obvious to the reader.

   when: reboot_required is defined and reboot_required == false

... again, I probably have the syntax wrong.

All of this presupposes that instead of directly checking components of a structured return value, you turn your various tests into a simple boolean as a separate operation; then afterwards you can use a much more readable "when: reboot_required". So in the stanzas where you have a structured value and are looking for a string in it, you would call the structured value something else, and generate reboot_required from it. Just a thought.

Regards, K.



For more options, visit https://groups.google.com/d/optout.


--
Karl Auer

Email  : ka...@2pisoftware.com
Website: http://2pisoftware.com


GPG/PGP : 958A 2647 6C44 D376 3D63 86A5 FFB2 20BC 0257 5816
Previous: F0AB 6C70 A49D 1927 6E05 81E7 AD95 268F 2AB6 40EA

Reply all
Reply to author
Forward
0 new messages