¿Systemd ExecStopPost no se ejecuta si ExecStartPre falla?

¿Systemd ExecStopPost no se ejecuta si ExecStartPre falla?

He repasado la documentación systemdaquí.https://www.freedesktop.org/software/systemd/man/systemd.service.html.

Lo dice en la ExecStartPre=,ExecStartPost=sección

Tenga en cuenta que si alguno de los comandos especificados en ExecStartPre=, ExecStart= o ExecStartPost= falla (y no tiene el prefijo "-", ver arriba) o se agota el tiempo de espera antes de que el servicio esté completamente operativo, la ejecución continúa con los comandos especificados en ExecStopPost= , los comandos en ExecStop= se omiten

tengo una ExecStartPreregla siendo

ExecStartPre=/bin/false

En ExecStopPosttengo un /bin/echo "I'm at ExecStopPost".

El servicio parece

[Unit]
Description=Test

[Service]
Type=oneshot
ExecStartPre=/bin/echo "I'm at ExecStartPre"
ExecStartPre=/bin/false
ExecStart=/bin/echo "Running Test"
ExecStopPost=/bin/echo "I'm at ExecStopPost"

Cuando se ejecuta y falla, nunca lo veo. La salida de syslog parece

15 de junio 20:48:01 ip-10-0-0-246 echo[8687]: Estoy en ExecStartPre

15 de junio 20:48:01 ip-10-0-0-246 systemd[1]: test.service: proceso de control salido, código = estado salido = 1

15 de junio 20:48:01 ip-10-0-0-246 systemd[1]: No se pudo iniciar la prueba.

15 de junio 20:48:01 ip-10-0-0-246 systemd[1]: test.service.service: La unidad entró en estado fallido.

15 de junio 20:48:01 ip-10-0-0-246 systemd[1]: test.service.service: Error con el resultado 'código de salida'.

Nunca veo mi eco.

journalctl -u test.servicePor supuesto, también tiene esto como entrada.

¿Necesito configurar esto de manera ligeramente diferente? ¿O necesito usar OnFailure?

Necesito poder reiniciar Conflicts=en casos de éxito o fracaso. Esto se utilizará en servicios oneshot activados por temporizadores.

Ah, y esto se ejecuta en 16.04.6 LTS.

Respuesta1

Parece que oneshotlos servicios no llaman.ExecStopPost al fracaso. Este enlace lo analiza.https://bugzilla.redhat.com/show_bug.cgi?id=1353039.

La publicación relevante es

ExecStopPost se ejecuta solo cuando la unidad pasa del estado de ejecución (incluso cuando la unidad se apaga) o cuando el PID principal sale exitosamente mientras está en el estado de activación y el servicio no es de tipo bifurcación.

La diferencia es que en el caso de un servicio de una sola vez mientras se ejecutan las acciones ExecStart configuradas, el servicio aún está en estado de activación y no se está ejecutando. Sin embargo, en el caso de un servicio simple, systemd cambia inmediatamente el servicio al estado de ejecución, systemctl no se bloquea y se devuelve la salida 0 incluso cuando ExecStart falla (es decir, ExecStart=/bin/false). Por lo tanto, el servicio oneshot debe salir limpiamente para poder llamar a ExecStopPost. AFAICT, la opción RemainAfterExit no tiene ningún impacto en ExecStopPost.

La solución terminó siendo agregar un OnFailurepara invocar los elementos necesarios que se habrían llamado enExecStopPost

información relacionada