Tutoriales de VPS
Corregir curl 60 SSL certificate problem en VPS (2026): CA, cadena y verificación de hostname
¿El navegador funciona pero curl falla al validar certificados? Distingue CA no fiable, cadena incompleta, hostname incorrecto y archivo CA inválido; corrige el entorno real manteniendo TLS.

¿curl en el VPS devuelve curl: (60) SSL certificate problem para una API HTTPS que abre en el navegador? No añadas -k a todos los scripts. El cliente no pudo validar el certificado; puede fallar confianza local, cadena del servidor, hostname o reloj.
Revisa conexión real, certificados y qué extremo corregir. Sirve para APIs, instalación y automatización. TLS falla antes del procesamiento HTTP; distingue 401, 403 y 404 de validación de certificados.
Comprueba en el mismo VPS, contenedor y usuario; sustituye el dominio:
curl --version
date -u
curl -v --connect-timeout 10 --max-time 30 https://api.example.com/
Revisa backend TLS, dirección, certificados y proxy. Distintas compilaciones usan almacenes CA diferentes. Que funcione el host no demuestra funcionamiento del contenedor o SDK. Quita Authorization, Cookie, credenciales de proxy y URLs sensibles antes de compartir -v.
| Mensaje o síntoma | Qué revisar | Corrección habitual |
|---|---|---|
unable to get local issuer certificate | Origen de CA e intermedios | Completar cadena o configurar CA correcta |
certificate has expired | Validez y hora actual | Certificado correcto o reloj corregido |
| Hostname no coincide | URL, DNS, SAN y SNI | Dominio y certificado correctos |
| Autofirmado o CA interna | Fuente de confianza clara | CA verificada para esa llamada |
| Archivo CA ilegible o inválido | Ruta, permisos y formato | Reparar archivo; puede ser error 77 |
La guía de verificación de curl incluye cadena y hostname de la URL. Navegador y curl pueden diferir en confianza, caché y completar cadenas. Que el navegador funcione no descarta configuración incorrecta del servidor.
Con OpenSSL, revisa handshake y certificados:
openssl s_client -connect api.example.com:443 \
-servername api.example.com -showcerts \
-verify_hostname api.example.com -verify_return_error </dev/null
-servername envía SNI y -verify_hostname verifica hostname: son operaciones distintas. -showcerts muestra certificados, no validación correcta. s_client puede continuar tras errores por defecto; -verify_return_error detiene aquí el handshake si falla.
Comprueba nombres, emisor y validez del certificado final e intermedios necesarios. Los sitios públicos suelen enviar final e intermedios; la raíz está normalmente en el cliente. Dos certificados o nombre fullchain.pem no prueban configuración correcta.
Si es tu Nginx, configura cadena completa según el emisor, valida sintaxis, recarga y repite. Para emisión o renovación, consulta diagnóstico de Let's Encrypt.
Certificado de api.example.com accedido por https://服务器IP/ puede fallar salvo SAN correspondiente a esa IP. Cambiar Host HTTP no cambia el nombre validado de la URL.
Para acceder directamente a un servidor, conserva el dominio y cambia resolución de esa conexión:
curl --resolve api.example.com:443:203.0.113.10 \
https://api.example.com/
Sustituye la IP documental por destino confirmado. --resolve no desactiva validación; la URL sigue definiendo TLS. Si solo un proxy confía en el certificado de origen, un cliente directo puede fallar. Revisa el diseño de confianza con Cloudflare 525 / 526 y certificados de origen.
Si varios sitios HTTPS normales fallan con hora y nombres correctos, revisa paquete CA ausente o antiguo y rutas personalizadas del sistema o imagen.
En Debian / Ubuntu con apt, repara o actualiza según mantenimiento:
sudo apt update
sudo apt install --reinstall ca-certificates
sudo update-ca-certificates
El manual update-ca-certificates explica confianza del sistema. No es universal para todo sistema o backend. El contenedor necesita su paquete; incluye la corrección en su build.
Revisa también --cacert, CURL_CA_BUNDLE, SSL_CERT_FILE y SSL_CERT_DIR. Identifica su aplicación antes de corregir; no vacíes configuración de producción sin criterio. Python, Java y Node.js pueden no reutilizar las CA de curl.
Obtén y verifica la CA por un canal fiable, sin confiar ciegamente en un certificado descargado de la conexión fallida. Para una llamada:
curl --cacert /path/to/verified-root-ca.pem https://internal.example.com/
Sigue verificando cadena y hostname; no valida certificados vencidos o nombres erróneos. Usa certificado PEM adecuado, no clave privada, web o página de error. El usuario de ejecución debe leer la ruta. --cacert depende del backend y opciones de curl.
Añadir CA interna global amplía confianza: sigue el proceso de la organización. Para una sola aplicación, considera configuración CA independiente admitida y registra rotación.
-k / --insecure omite validación. Solo indica que al saltarla continúa la conexión, sin distinguir intermedio ausente, CA desconocida o sitio incorrecto. No lo dejes como solución en producción, instalación o tareas programadas.
Repite el comando real sin -k en su entorno. Confirma TLS y después respuesta HTTP y aplicación esperadas. Un 401 o 404 posterior exige autenticación o rutas, no más cambios CA.
El artículo original documenta 6 pruebas locales en macOS con curl 8.7.1 (SecureTransport) y OpenSSL 3.6.0: intermedios ausentes, CA no fiable y hostname erróneo produjeron curl 60; cadena completa y CA indicada devolvieron 200; archivo CA ausente causó 77; OpenSSL validó cadena y nombre. Se usaron certificados temporales y loopback sin modificar confianza del sistema. No abarcan renovación pública, paquetes Ubuntu, proxies, imágenes de contenedor ni SDKs reales.