Respuesta para 2021

Respuesta para 2021

Estoy usando Ansible para verificar los hosts si es necesario reiniciarlos si el /vmlinuzkernel no resuelve uname -r.

La ifcondición es, aunque siempre se identifica un reinicio, aunque la máquina de prueba se haya reiniciado y el kernel se esté resolviendo en el mismo kernel:

if [ $(readlink -f /vmlinuz) != /boot/vmlinuz-$(uname -r) ]; luego haga eco de 'reiniciar'; de lo contrario, haga eco de 'no'; fi

- name: Check for reboot hint.
  shell: if [ $(readlink -f /vmlinuz) != /boot/vmlinuz-$(uname -r) ]; then echo 'reboot'; else echo 'no'; fi
  ignore_errors: true
  register: reboot_hint

- name: Rebooting ...
  command: shutdown -r now "Ansible kernel update applied"
  async: 0
  poll: 0
  ignore_errors: true
  when: kernelup|changed or reboot_hint.stdout.find("reboot") != -1
  register: rebooting

- name: Wait for thing to reboot...
  pause: seconds=45
  when: rebooting|changed

Respuesta1

Puede determinar de manera confiable la última versión del kernel instalada mediante la siguiente consulta rpm:

rpm -q kernel --queryformat '%{installtime} %{version}-%{release}.%{arch}\n' | sort -n -k1 | tail -1 | cut -d ' ' -f 2

Salida de muestra en RHEL 7:

3.10.0-229.11.1.el7.x86_64

Ahora sólo comprueba si la salida de uname -rcoincidencias:

3.10.0-229.1.2.el7.x86_64

En este ejemplo, no coincide y es necesario reiniciar.

Podrías usar test para comparar las cadenas:

if [ "`rpm -q kernel --queryformat '%{installtime} %{version}-%{release}.%{arch}\n' | sort -n -k1 | tail -1 | cut -d ' ' -f 2`" = "`uname -r`" ]; then echo "latest kernel already booted."; else echo "new kernel. reboot required."; fi

Respuesta2

Respuesta para 2021

Como @kawing-chiu mencionó ensu respuesta, dnfahora tiene un needs-restartingmódulo que hace exactamente lo que requiere la pregunta. Determina si los paquetes del sistema se han actualizado desde el último arranque, aunque eso no se limita únicamente a los cambios del kernel. Podría decirse que este comportamiento es mejor que simplemente comparar la versión del kernel con los paquetes instalados.

needs-restartingNo se puede acceder al módulo dnf a través del ansible.builtin.dnfmódulo Ansible, pero se puede llamar a través ansible.builtin.shellde ansible.builtin.commandsu alias needs-restarting -r, más directamente con dnf needs-restarting -ro incluso más explícitamente con /usr/bin/dnf needs-restarting -r.

La -rbandera no parece requerir privilegios de root y simplemente informa si es necesario reiniciar. El código de retorno es 0si no es necesario reiniciar y 1si lo es. Por lo tanto, deberíamos poder utilizar una tarea como esta, que está adaptada de la sugerida porJoel Cattin:

- name: Check if a reboot is required
  ansible.builtin.command: needs-restarting -r
  register: reg_reboot_required
  ignore_errors: yes
  failed_when: false
  changed_when: reg_reboot_required.rc != 0
  notify:
    - Reboot server 

También necesitará un controlador nombrado o escuchando Reboot serverpara llevar a cabo la tarea de reinicio. Algo como esto funcionará:

- name : Reboot server
  ansible.builtin.reboot:
    msg: "Reboot initiated by Ansible after OS update"
    reboot_timeout: 3600
    test_command: uptime

Espero que esta respuesta ayude a cualquiera que venga buscando una solución a este problema.

Respuesta3

Hilo ANTIGUO, pero esto me ayudó a crear este script ansible rápido que podría ayudar a alguien.

---
- hosts: allhosts
  gather_facts: False
  tasks:
    - name: check latest kernel installed
      shell: rpm -q kernel --queryformat '%{installtime} %{version}-%{release}.%{arch}\n' | sort -n -k1 | tail -1 | cut -d ' ' -f 2
      register: kernel_installed_latest
    - name: Check running kernel version
      shell: uname -r
      register: kernel_version
    - fail:
        msg: "latest kernel version {{kernel_installed_latest.stdout}} doesnt match running kernel {{kernel_version.stdout}}"
      when: (kernel_installed_latest.stdout != kernel_version.stdout)

Respuesta4

Otra alternativa es realizar las actualizaciones del kernel por separado y activar un controlador para reiniciar el sistema si se requiere la actualización del kernel.

  tasks
  - name: Upgrade all packages, excluding kernel
    ansible.builtin.yum:
      name: '*'
      state: latest
      exclude: kernel*
  - name: Upgrade kernel
    ansible.builtin.yum:
      name: 'kernel*'
      state: latest
    notify: restart host
  handlers:
    - name: restart host
      ansible.builtin.reboot:

información relacionada