Certificados SSH: una mejor experiencia con SSH
(jpmens.net)- Los certificados SSH resuelven las complicaciones de la autenticación SSH tradicional basada en claves públicas y proporcionan confianza automática entre cliente y servidor
- Son compatibles desde OpenSSH 5.4, y una CA (autoridad certificadora) firma las claves de usuario y de host para permitir la autenticación sin modificar
authorized_keys - Los certificados pueden incluir período de validez, usuarios permitidos (principal), IP de acceso, comando forzado (force-command) y más, lo que permite un control de acceso detallado
- Se elimina el proceso de TOFU (Trust on First Use) y es posible conectarse de forma segura sin advertencias cuando cambia la clave del host
- Con un servidor o herramientas de firmado automático, es posible automatizar la gestión de SSH en entornos con muchos servidores y mejorar la seguridad
Panorama general de los certificados SSH y límites de la autenticación SSH tradicional basada en claves
- Al conectarse por SSH, es necesario verificar la huella digital (fingerprint) de la clave del host del servidor la primera vez; sin embargo, la mayoría de los usuarios no la valida y usa el método TOFU (Trust on First Use) escribiendo simplemente “yes”
- Los administradores pueden comprobar la huella directamente en el servidor o validarla con el comando
ssh-keygen -l -f /etc/ssh/ssh_host_ed25519_key
- Los administradores pueden comprobar la huella directamente en el servidor o validarla con el comando
- La autenticación basada en claves públicas permite conectarse sin contraseña, pero requiere distribuir la clave pública en el archivo
authorized_keysde cada servidor - Con el agente SSH (
ssh-agent), la clave privada puede mantenerse en memoria para autenticarse repetidamente sin volver a ingresarla - Limitaciones del método tradicional
- Es necesario copiar la clave pública a los servidores para cada usuario
- Cuando cambia la clave del host, el cliente muestra un mensaje de advertencia
- La gestión de confianza con TOFU resulta incómoda
Certificados SSH y autoridad certificadora (CA)
- Los certificados SSH (Certificate) son compatibles desde OpenSSH 5.4 (marzo de 2010) y extienden el formato tradicional de claves SSH
- Una CA de SSH se compone de un par de claves SSH, donde la clave pública actúa como raíz de confianza
- Principales ventajas
- No es necesario modificar el archivo
authorized_keysdel servidor - No hay advertencias al reemplazar la clave del host
- La eliminación del proceso TOFU permite implementar confianza automática
- El certificado puede incluir usuarios permitidos (principal), IP permitidas, período de validez, comando forzado (force-command) y más
- El acceso se bloquea automáticamente cuando el certificado expira
- No es necesario modificar el archivo
Implementación de una CA SSH y proceso de firmado
- En el sistema CA, se genera un par de claves de CA con el algoritmo ECDSA
ssh-keygen -t ecdsa -C "SSH CA" -f CA/ssh-ca
- El usuario entrega su clave pública (
*.pub) a la CA, y la CA la firma (sign) para emitir un certificado (*-cert.pub)- Ejemplo:
ssh-keygen -s CA/ssh-ca -I "Jane Jolie" -n jane -z 001 -V +1w jane.pub
- Ejemplo:
- Configuración del servidor
- Guardar la clave pública de la CA en
/etc/ssh/ssh-ca.puby agregar la opciónTrustedUserCAKeys - Firmar la clave de host del servidor con la CA (
ssh-keygen -h -s CA/ssh-ca ...) y registrarla en la opciónHostCertificate
- Guardar la clave pública de la CA en
- Configuración del cliente
- Agregar una línea
@cert-authorityen el archivoknown_hosts - Ejemplo:
@cert-authority *.example.com $(cat CA/ssh-ca.pub)
- Agregar una línea
Conexión y verificación basadas en certificados SSH
- El usuario se conecta usando el certificado firmado junto con la clave privada (
ssh -i jane -l jane alice.example.com) - En los registros del servidor se guardan el ID, el número de serie (serial) y la huella de la CA del certificado
- Se pueden agregar varios nombres de host o direcciones IP como principal del certificado
- Si se intenta iniciar sesión como un usuario distinto de los principals definidos en el certificado, aparece el error “Certificate invalid: name is not a listed principal”
- Es posible aplicar controles detallados de acceso configurando comando forzado (force-command) o IP permitidas (source-address) en el certificado
Lista de verificación para revisión y solución de problemas
-
Elementos a revisar del lado del servidor
- Configuración de
TrustedUserCAKeysy existencia de la clave pública de la CA - Firmado de la clave de host y configuración de
HostCertificate - Es necesario reiniciar
sshd
- Configuración de
-
Elementos a revisar del lado del cliente
- La clave del usuario debe estar firmada por la CA
- La entrada
@cert-authorityenknown_hostsy el principal deben coincidir - Cuando el certificado expira, aparece el mensaje “Certificate invalid: expired”
- Si no coinciden las restricciones del certificado, se solicitará contraseña
- Al agregar el certificado al agente SSH, se registran tanto la clave como el certificado (
ssh-add jane) - Es posible controlar funciones con opciones (
-O) al firmar - Ejemplo: con
-O clearse eliminan todos los permisos y solo se permitenpermit-agent-forwardingypermit-port-forwarding
Automatización de certificados de claves de host
- Con el módulo de Python sshkey-tools y BottlePy se puede implementar un servidor de firmado automático (hkbot)
- En el servidor CA, ejecutar
hkbot.py; después, al subir la clave pública del host mediante una solicitud HTTP, se firma automáticamente - En el cliente, usar el comando
curl -F hostkey=@/etc/ssh/ssh_host_ed25519_key.pub http://CA:8870 | shpara la instalación automática - Se aplica tras modificar
/etc/ssh/sshd_config, validarlo y ejecutarsystemctl restart sshd
- En el servidor CA, ejecutar
- Después, las conexiones SSH pueden realizarse con confianza automática e inicio de sesión basado en certificados
Resumen de ventajas de los certificados SSH
- No se necesita TOFU, hay confianza automática entre cliente y servidor
- Se pueden emitir certificados de corta duración para controlar accesos temporales
- Cuando el certificado expira, el acceso se bloquea automáticamente y no hace falta limpiar
authorized_keys - Es posible aplicar políticas detalladas como comando forzado, restricción de PTY y control por IP de acceso
- Con herramientas de automatización, se puede simplificar la gestión en entornos con muchos servidores
- Se presenta Smallstep SSH como proyecto relacionado
Material adicional de referencia
- Guía de seguridad de OpenSSH de Mozilla
- Artículo de investigación sobre validación de huellas de claves de host SSH basada en DNS
- Documentación de implementación de soporte de certificados OpenSSH en PuTTY y guía de configuración
Actualización
- Una CA SSH es especialmente útil en entornos con servidores propios y acceso root
- En sistemas multiusuario, siguen siendo necesarios los métodos tradicionales con
known_hostsyauthorized_keys - Borrador de estandarización del formato de certificados SSH:
draft-miller-ssh-cert-06
1 comentarios
Comentarios de Hacker News
Sorprende que la gente todavía use contraseñas de SSH
especialmente en entornos de grandes empresas, donde se cruzan múltiples políticas de contraseñas, así que incluso conectarse a un servidor toma tiempo
por eso, aunque les digas que usen llaves con ssh-keygen, la mayoría responde “algún día lo pruebo” y al final nunca lo hace
pero en la práctica es fácil que la gestión sea un desastre, usando una misma llave pública en varios servidores o incluso compartiendo llaves
al menos las contraseñas tienen la ventaja de ser simples
no tiene contraseña, pero al iniciar sesión tengo que tocar físicamente la Yubikey
Cada pocos meses alguien vuelve a descubrir los certificados SSH y escribe una entrada de blog al respecto
yo también escribí sobre eso hace 15 años, pero ahora veo que se quedó corto
incluso los ingenieros de seguridad a veces olvidan que están usando autenticación por llaves y no certificados SSH
administrar manualmente las llaves de varios servidores es demasiado tedioso
ahora estoy pensando si todavía vale la pena hacer el cambio
El enfoque TOFU (Trust On First Use) es simple, pero llega bastante lejos
en mis servidores, una vez que verifico directamente la llave del host, con eso basta
en un entorno corporativo grande, basta con publicar la lista de llaves públicas de los servidores internos en un sitio web interno firmado con SSL
pero cuando hay muchos servidores o cambian con frecuencia, los certificados son mucho mejores y TOFU tiene límites en varios sentidos
también me gustaría que los navegadores avisaran cuando cambia la llave TLS de un servidor
casi todos simplemente escriben “yes” y siguen adelante
En la empresa hemos desperdiciado muchísimo tiempo y dinero por la inspección SSL de Zscaler
cuando aparece el error “self-signed certificate in certificate chain”, siempre es un dolor de cabeza
mete su propio certificado raíz y bloquea la configuración del navegador para impedir el uso de proxy
aunque modifiques los archivos de configuración de Firefox o Chrome, los sobreescribe de inmediato
incluso para desactivarlo desde la GUI necesitas la contraseña de TI
apenas es un poco mejor que el antivirus de Cybereason
rompe todos los protocolos basados en HTTP
se rompen Git, RubyGems, go mod, Nix y muchísimas otras herramientas
el proveedor dice que es “transparente”, pero en la práctica no lo es en absoluto
diagnosticar el problema toma horas y la mayoría de los administradores no sabe lo destructivo que puede ser
El texto solo menciona las ventajas de los certificados de CA, pero también hay desventajas claras
yo nunca he sufrido un problema de seguridad por TOFU
si los certificados SSH tienen desventajas, me gustaría saber exactamente cuáles son
si quieres reforzar la seguridad, puedes intercambiar llaves públicas por un canal seguro como USB
incluso usando certificados, al final sigues el mismo proceso; solo cambia quién administra, del usuario al administrador
en organizaciones grandes los certificados pueden ser útiles, pero la seguridad general es la misma
basta con incluirla en el script de instalación o en la imagen de despliegue
TOFU solo tiene sentido cuando accedes a una máquina ya configurada
En nuestro entorno dev/stg reinstalamos la mitad de las máquinas todos los días
gracias a los certificados de host SSH, es mucho más cómodo porque no hace falta borrar
known_hostsni conservar las llavesEstoy creando una herramienta llamada Sshifu como proyecto personal
es una herramienta para facilitar el inicio de sesión con certificados SSH y SSO
instalas sshifu-server en el servidor para usarlo como CA, y configuras cada servidor SSH para que confíe en esa CA
el usuario solo tiene que iniciar sesión con el comando
npx sshifuconsulta el repositorio en GitHub
En entornos reales de operación, el acceso basado en certificados lleva a problemas de administración complejos
aparecen temas como vencimiento de certificados, eliminación de usuarios e inicio de sesión cuando un servidor falla
llevamos 15 años tratando estos problemas en Userify, y construir una infraestructura de autenticación SSH estable no es nada sencillo
Añadí soporte para certificados SSH a pico.sh, y fue muy útil porque permitió implementar control de acceso estilo RBAC
consulta la documentación
En producción, los certificados SSH más bien centralizan la complejidad y agravan el problema
una sola CA debe estar siempre disponible, y si falla, se bloquea todo el acceso
también hay muchos problemas reales como ajustar el TTL, administrar la raíz de confianza y la dificultad para depurar
al final la gente vuelve a introducir cachés o agentes
nosotros hacemos lo contrario: cada nodo sincroniza por HTTPS la información de usuarios hacia el authorized_keys local
así se mantiene el control centralizado, pero las fallas quedan localizadas
en Userify usamos este enfoque, y no solo para autenticación sino también para gestión de permisos
solo con certificados no se resuelven problemas como la creación de usuarios, roles de sudo o limpieza del directorio home