¿Puede un script de enlace de OpenVPN usar el túnel que acaba de crear?
OpenVPN ejecuta los enlaces dentro de su propio arranque, así que un script que necesita el túnel espera a un túnel que lo espera a él. Separe el trabajo y elija el enlace según el evento.
Que un script de enlace llegue al otro lado del túnel depende de tres condiciones: a qué evento está ligado, si OpenVPN sigue dentro de su secuencia de arranque cuando se ejecuta el script y si el trabajo se ha separado de esa secuencia. La mayoría de los scripts fallan en la tercera. Añadir una espera trata un problema de ciclo de vida como un problema de tiempos, y funciona justo lo bastante a menudo para engañar.
Decida primero el evento, después el mecanismo para aplazar el trabajo y después el lugar donde se ejecuta el trabajo aplazado. Esas tres decisiones son independientes, y mezclarlas es cómo un enlace de dos líneas se convierte en una tarde entera.
Por qué el enlace espera a un túnel que lo espera a él
OpenVPN llama a sus enlaces de forma síncrona, dentro del mismo proceso que mueve los paquetes. up se dispara cuando existe el dispositivo tun o tap, pero antes de que se añada cualquier ruta, y route-up se dispara después de las rutas; ninguno de esos momentos promete que un par responda. Mientras un script de cualquiera de los enlaces sigue ejecutándose, el demonio no reenvía, así que un comando que espera que el tráfico cruce el túnel espera a un túnel que espera al comando. Esa espera circular es la razón por la que una ejecución manual pasa y el enlace agota el tiempo.
El parche obvio, dormir unos segundos, a veces funciona porque el extremo remoto subió solo, no porque la espera arreglara nada. Un ayudante que sondea la disponibilidad es otra respuesta: el enlace vuelve, el reenvío empieza y el ayudante obtiene lo que necesita cuando de verdad está ahí.
Elija el enlace por evento, no por comodidad
Ate up al trabajo que solo necesita el dispositivo, route-up al trabajo que necesita rutas, y reserve client-connect y client-disconnect para tareas por cliente en el lado del servidor. La limpieza al desconectar debe tolerar ejecutarse dos veces, ya que las reconexiones sobre una interfaz persistente no siguen la misma secuencia que un reinicio completo. En el servidor, client-connect se dispara cuando un cliente se autentica, no cuando arranca el demonio, algo que conviene confirmar antes de mover allí la lógica. Si el trabajo pertenece al ciclo de vida del servicio y no a una sola conexión, una unidad de systemd es un hogar mejor que cualquier enlace.
Los comandos de enlace los ejecuta directamente el demonio, sin ningún shell en medio, así que ifconfig_remote en una línea up llega como texto literal. Envuelva el comando en un shell explícito o mantenga la lógica en un script que lea el entorno. ipchange es una directiva que añade argumentos propios: entrega la dirección y el puerto al comando, así que un script escrito para ninguno ve dos inesperados.
Tres formas de separar el trabajo
La primera opción es enviar al ayudante al fondo desde dentro del enlace: inícielo con setsid o systemd-run --scope, cierre los descriptores heredados y salga con cero de inmediato. La segunda es que el enlace escriba un pequeño archivo de estado y que un temporizador de systemd o una unidad de ruta actúen sobre él, lo que mantiene el enlace trivial y pone la política de reintentos donde hay registros. La tercera es descartar el enlace por completo y mover el trabajo a una unidad ordenada después del servicio VPN, que es la respuesta correcta cuando el trabajo no es por conexión en absoluto. Las tres comparten una regla: el enlace debe volver antes de necesitar el túnel.
Elija lo que elija, haga el ayudante idempotente y observable. Dos invocaciones solapadas no deberían ejecutar la misma acción irreversible dos veces, y un ayudante que falla tiene que dejar algo que una persona pueda leer.
Separe los fallos de sandbox de los fallos de ciclo de vida
Cuando un script se ejecuta desde un indicador de root y falla como servicio, la causa suele ser una sandbox y no la red. Una ProtectHome restrictiva, una ProtectSystem de solo lectura o un directorio de trabajo que no existe pueden dejar el script o sus datos inalcanzables, y en un host SELinux el archivo también necesita un contexto que permita la ejecución. Lea la unidad con systemctl cat openvpn-server@server y el registro con journalctl -u openvpn-server@server -n 80, y luego busque un error de permisos o de contexto en lugar de un tiempo de espera de conexión. Desactivar la sandbox debería ser el último movimiento, no el primero.
Un fallo de ciclo de vida se ve distinto: el enlace arranca, el ayudante corre y el socket simplemente aún no está. Escriba una línea con marca de tiempo desde el propio enlace, desconecte y reconecte, y lea los eventos en orden. Cuando el ayudante necesite de verdad el túnel, déjelo sondear la disponibilidad en lugar de dormir un periodo fijo.
Tres campos hacen útil el siguiente informe: qué enlace se ejecutó, qué cuenta usó y dónde se detuvo. Sin ellos, cada investigación posterior empieza de cero.