Llegar a una interfaz web dentro de un contenedor VPN: elija al dueño del puerto
La aplicación comparte el espacio de nombres de la VPN, así que el puerto pertenece al contenedor VPN. Enlace el oyente correctamente, publique en el dueño y mantenga el camino estrecho.
Nada está mal en la aplicación y nada está mal en el túnel, y aun así el panel no carga. Cuando un servicio se ejecuta con network_mode: service:vpn, comparte el espacio de nombres de red del contenedor VPN, lo que significa que su oyente y sus puertos publicados pertenecen a ese espacio de nombres y no al servicio. De ahí se siguen tres decisiones: dónde enlaza la aplicación, qué contenedor publica el puerto y cuán estrecho es el camino de gestión. Póngalas en el orden equivocado y cada ajuste individual parecerá correcto mientras la combinación no puede funcionar.
Quién posee el espacio de nombres del puerto
Con un espacio de nombres compartido, añadir una entrada ports: al servicio dependiente no hace nada útil, y varias opciones de red no son compatibles con él por diseño. Publique en el contenedor que posee el espacio de nombres. Ese contenedor es también aquel cuya dirección aparece en el host, así que la asignación se lee como una entrada y no una por servicio.
services:
vpn:
image: vpn-client-image
cap_add: [NET_ADMIN]
ports:
- "127.0.0.1:8080:8080"
app:
network_mode: "service:vpn"
Fíjese en la dirección a la izquierda de la asignación. Enlazar a 127.0.0.1 mantiene el puerto publicado en el loopback del host, que suele ser lo que quiere una interfaz de gestión. Enlazar a 0.0.0.0 lo expone en todas las interfaces del host, y eso es una decisión de seguridad distinta, no una comodidad.
Haga que la aplicación escuche donde el espacio de nombres espera
Un oyente enlazado a 127.0.0.1 dentro del espacio de nombres solo es accesible desde dentro de ese espacio. Los puertos publicados del host llegan desde fuera, así que la aplicación debe enlazar una dirección más amplia para que la asignación funcione. Eso es un cambio de una línea en la mayoría de servidores, y es el paso que la gente se salta después de copiar una guía de endurecimiento escrita para un despliegue sin contenedores.
docker compose exec app ss -lntp
docker port vpn
curl -sS -o /dev/null -w '%{http_code}\n' http://127.0.0.1:8080/
El listado de oyentes dentro de la aplicación dice la verdad sobre la dirección de enlace, y docker port dice qué publicó realmente el dueño. Si el primero muestra 127.0.0.1 y el segundo muestra una asignación en el host, ha encontrado el desajuste sin tocar la configuración de la VPN.
Elija cómo entra el camino de gestión
Hay tres disposiciones razonables. Publique en el contenedor VPN y llegue a él desde el host o la red local. Ponga un proxy inverso delante del espacio de nombres y dé al proxy el único puerto expuesto. O mantenga el panel accesible solo desde dentro del espacio de nombres mediante una sesión exec o un túnel SSH, que es la menor exposición y la menor comodidad.
Cuál encaja depende de quién necesita la interfaz y desde dónde. Un solo administrador en el mismo host queda servido por un enlace de loopback. Un equipo que llega a ella a través de la VPN necesita un camino deliberado y un dueño con nombre. Elegir la opción del proxy le da TLS y registros de acceso, a cambio de otro componente que mantener actualizado.
Abra el puerto de gestión sin abrirlo todo
La propia política de acceso local o de bloqueo del cliente VPN puede descartar una solicitud de gestión entrante incluso mientras el túnel saliente funciona perfectamente. Permita una excepción documentada para el origen y el puerto previstos, y luego confirme que la protección ordinaria del túnel no ha cambiado. Desactivar el kill switch para que cargue un panel cambia un control real por una pestaña del navegador.
Deje activada la autenticación propia de la aplicación. Estar dentro de una pila conectada a la VPN no autoriza a cada usuario local ni a cada dispositivo que pueda llegar al host, y un panel de administración sin autenticación detrás de un túnel sigue siendo un panel de administración sin autenticación.
Verifique desde el dispositivo de gestión y vuelva a verificar más tarde
Pruebe desde la máquina que realmente gestionará el servicio, no desde el host, y luego verifique por separado el camino de internet que la aplicación necesita. Un éxito de gestión demuestra una dirección y no dice nada sobre la salida.
Vuelva a probar después de que se recree la pila. Un dueño de red reemplazado cambia el espacio de nombres al que se adhiere la aplicación, y una URL que funcionaba antes de una actualización puede no apuntar a nada después. Anote la asignación publicada y la dirección de enlace para que la próxima reconstrucción sea una comprobación de dos minutos en lugar de una investigación repetida.