miércoles, 6 de septiembre de 2023

Script para reiniciar servicios de zypper ps -s



Cómo reiniciar de golpe todos los servcios afectados por la actualización de un SUSE Linux Enterprise Server, script para reiniciar todos los servicios que aparecen en la lista zypper ps -s.



Tal y como ya comenté en su momento, tras actualizar un SUSE Linux Enterprise Server, puede que el sistema muestre el siguiente mensaje como última línea del output de la actualización:

... There are some running programs that might use files deleted by recent upgrade. You may wish to check and restart some of them. Run 'zypper ps -s' to list these programs.

Al ejecutar zypper ps -s, veremos una lista con los servicios afectados por el proceso de actualización.

HOST# zypper ps -s The following running processes use deleted files: PID | PPID | UID | User       | Command                    | Service ----+------+-----+------------+----------------------------+----------------- 458 | 1    | 0   | root       | systemd-journald (deleted) | systemd-journald 462 | 1    | 0   | root       | haveged                    | haveged 843 | 1    | 4   | messagebus | dbus-daemon                | dbus 872 | 1    | 0   | root       | irqbalance                 | irqbalance You may wish to restart these processes. See 'man zypper' for information about the meaning of values in the above table.

Estos servicios deben reiniciarse para evitar problemas de funcionamiento en las aplicaciones señaladas. Para reiniciarlos, o bien reiniciamos cada servicio uno a uno, o bien reiniciamos la máquina (recomendable, aunque no siempre es posible. Sobretodo si está en producción).

Si son solo un par o tres de servicios, podemos reiniciarlos uno a uno manualmente, pero cuando la lista es de 30 servicios, como la que me encontré yo tras la última actualización que llevé a cabo, el proceso se hace engorroso. Por suerte, tenemos bash para automatizar la tarea. Bash nos permite coger la lista de servicios, iterar sobre esa lista e ir reiniciando los servicios uno a uno de forma desatendida.

El script que hice para realizar esta tarea es el siguiente:

#!/usr/bin/env bash

TOTAL=$(zypper ps -s | awk '($1+0)' | awk '{print $11}' | awk -F, 'length($1)' | wc -l);

echo "Reiniciando $TOTAL servicios..."

zypper ps -s | awk '($1+0)' | awk '{print $11}' | awk -F, 'length($1)' | while read line
do
   service $line restart;
done

TOTAL es una variable que cuenta (wc -l) los procesos de zypper ps -s para mostrar luego al usuario cuántos servicios se van a reiniciar (a modo informativo).

awk '($1+0)' muestra en en pantalla solamente las líneas que empiecen con un número. Así, evitamos mostrar los títulos de la tabla y los separadores y nos centramos solo en las filas que contienen nombres de servicios. Recordemos que las filas con los servicios empiezan con un número de proceso.

awk '{print $11}' muestra solamente la información de la columna 11 de cada fila. En el caso que nos ocupa, el nombre de servicio se muestra en la columna número 11.

awk -F, 'length($1)' solo muestra el valor de la columna si este valor tiene longitud (es decir, si el número de caracteres de esa columna es mayor que 0). Así, evitamos errores poducto de ejecutar "service (espacio en blanco) restart", ya que algunas filas no tienen nombre de servicio, por lo que he podido ver.

Por último, usamos un while para tratar la información. Traducido sería "mientras pueda leer una línea del output que me está pasando la cadena de comandos anterior, realizar la siguiente acción". Y la siguiente acción es reiniciar el servicio.

Como no he redirigido los errores fuera del canal estándar de salida, si el reinicio de algún servicio falla, veremos el log de error en pantalla, igual que lo veríamos si hubiéramos reiniciado cada uno de los servicios manualmente.
0