mail - GoDaddy SSL Cert no funciona con Java
smtp en java (10)
UPDATE 1/26/2015 -- It appears the most recent JRE/JDK for Java 8 (update >= 31) and JRE/JDK for Java 7 now include the Godaddy G2 CA server in the default trust store. If possible, it''s urged you upgrade your JRE/JDK to the latest Java 8 update to resolve this issue.
ACTUALIZACIÓN 29/11/2014 - Esto sigue siendo un problema, y parece que Godaddy no se preocupa ni hará nada al respecto. Hay una publicación en el blog here por Godaddy VP de Security Products desde hace varios meses diciendo que había una solución en su camino y que proporcionaba una solución temporal, pero a partir de hoy, nada ha cambiado. Es importante tener en cuenta que el servidor Godaddy''s G2 CA ha existido por un mínimo de 5 años, y en ese momento Godaddy no ha tomado las medidas adecuadas para resolver este problema conocido. La solución provista es solo eso, una solución alternativa, no una solución. Los usuarios de servicios de terceros no tienen control sobre cómo se instala el certificado en el servidor.
It seems users should avoid purchasing Godaddy SSL certs until they get serious about being a CA.
Aquí está la información de contacto de su equipo SSL si se siente inclinado a llamar:
GoDaddy SSL Team Support Number: 1-480-505-8852 -- Email: [email protected]
ACTUALIZACIÓN 17/09/2014 - Esto sigue siendo un problema, y parece que Godaddy no se preocupa ni hará nada al respecto. En noviembre, cuando Google derogue todos los certificados de SHA-1, se convertirá en un problema importante. Recomiendo encarecidamente a cualquiera que pueda contactar a Godaddy y señalarlos aquí.
~
tl;dr; - final update with current solution/workaround at the bottom of this post (it is a GoDaddy problem and there is a workaround until they fix it)
Tengo un servidor de correo al que estoy intentando enviar correo desde mi aplicación Java. Puedo enviar el puerto 25 con éxito, así sé que el código funciona y todo, pero el 25 no es una sesión cifrada. Necesito usar TLS en el puerto 587 que requiere un certificado SSL. Tengo un certificado SSL válido en el servidor que está firmado por GoDaddy G2 CA y ha estado en funcionamiento desde hace un tiempo (sin problemas).
Mi problema es que me está PKIX path building failed: sun.security.provider.certpath.SunCertPathBuilderException: unable to find valid certification path to requested target
la famosa PKIX path building failed: sun.security.provider.certpath.SunCertPathBuilderException: unable to find valid certification path to requested target
mensaje de error de PKIX path building failed: sun.security.provider.certpath.SunCertPathBuilderException: unable to find valid certification path to requested target
cuando intento conectarme y enviar correo en 587.
Desde mi entendimiento de muchos enlaces SO, así como de google-fu normal, esto generalmente se produce cuando Java no confía en el certificado o CA, como es común para un certificado autofirmado. He utilizado varias de las comprobaciones SSL Cert en línea para asegurarme de que la cadena sea válida, etc. Todo parece ser normal ... pero java no usará el certificado automáticamente.
Soy consciente de que hay un archivo de clase en alguna parte de Sun que descargará y configurará el certificado en el almacén de claves local para que java confíe en él ... pero esto no solo es poco práctico para una aplicación que se implementará en varios sistemas, sino que solo tonto para un certificado firmado por Godaddy.
¿Que esta pasando? ¿Cómo puedo hacer que Java use el certificado válido en el servidor sin tener que hacer que java acepte todos los certificados?
EDITAR: Acabo de buscar en mi Windows Java Control Panel (instalación predeterminada de jdk 7) y con certeza, bajo Signer CA
el Issued By: The Go Daddy Group, Inc. Go Daddy Class 2 Certification Authority
... así que lo que da ? Mi certificado es un certificado de Godaddy ...
UPDATE --
Aquí está la cadena de cert como se ve desde el comando openssl recomendado en los comentarios:
~]# openssl s_client -connect smtp.somecompany.com:587 -starttls smtp
CONNECTED(00000003)
depth=2 C = US, ST = Arizona, L = Scottsdale, O = "GoDaddy.com, Inc.", CN = Go Daddy Root Certificate Authority - G2
verify error:num=19:self signed certificate in certificate chain
verify return:0
---
Certificate chain
0 s:/OU=Domain Control Validated/CN=smtp.somecompany.com
i:/C=US/ST=Arizona/L=Scottsdale/O=GoDaddy.com, Inc./OU=http://certs.godaddy.com/repository//CN=Go Daddy Secure Certificate Authority - G2
1 s:/C=US/ST=Arizona/L=Scottsdale/O=GoDaddy.com, Inc./OU=http://certs.godaddy.com/repository//CN=Go Daddy Secure Certificate Authority - G2
i:/C=US/ST=Arizona/L=Scottsdale/O=GoDaddy.com, Inc./CN=Go Daddy Root Certificate Authority - G2
2 s:/C=US/ST=Arizona/L=Scottsdale/O=GoDaddy.com, Inc./CN=Go Daddy Root Certificate Authority - G2
i:/C=US/ST=Arizona/L=Scottsdale/O=GoDaddy.com, Inc./CN=Go Daddy Root Certificate Authority - G2
3 s:/C=US/ST=Arizona/L=Scottsdale/O=GoDaddy.com, Inc./OU=http://certs.godaddy.com/repository//CN=Go Daddy Secure Certificate Authority - G2
i:/C=US/ST=Arizona/L=Scottsdale/O=GoDaddy.com, Inc./CN=Go Daddy Root Certificate Authority - G2
---
Me parece bien, creo ...
UPDATE 2 --
Ok, gracias a @Bruno pude determinar que mi cadena estaba en mal estado: cambié la clave del servidor y ahora mi cadena aparece como tal:
~]# openssl s_client -connect smtp.somecompany.com:587 -starttls smtp
CONNECTED(00000003)
depth=2 C = US, ST = Arizona, L = Scottsdale, O = "GoDaddy.com, Inc.", CN = Go Daddy Root Certificate Authority - G2
verify error:num=19:self signed certificate in certificate chain
verify return:0
---
Certificate chain
0 s:/OU=Domain Control Validated/CN=smtp.somecompany.com
i:/C=US/ST=Arizona/L=Scottsdale/O=GoDaddy.com, Inc./OU=http://certs.godaddy.com/repository//CN=Go Daddy Secure Certificate Authority - G2
1 s:/C=US/ST=Arizona/L=Scottsdale/O=GoDaddy.com, Inc./OU=http://certs.godaddy.com/repository//CN=Go Daddy Secure Certificate Authority - G2
i:/C=US/ST=Arizona/L=Scottsdale/O=GoDaddy.com, Inc./CN=Go Daddy Root Certificate Authority - G2
2 s:/C=US/ST=Arizona/L=Scottsdale/O=GoDaddy.com, Inc./CN=Go Daddy Root Certificate Authority - G2
i:/C=US/ST=Arizona/L=Scottsdale/O=GoDaddy.com, Inc./CN=Go Daddy Root Certificate Authority - G2
---
Lo cual se ve mejor que antes. - Java todavía arroja la misma excepción sobre la ruta de certificación, etc. Por lo tanto, parece que la cadena de certificaciones G2 no es, de forma predeterminada, confiable aún en el almacén de claves predeterminado de java 7.
FINAL UPDATE FOR COMPLETENESS @ 1/14/2014
Solo como una actualización: este es realmente un problema de GoDaddy (he tenido largos correos de soporte con ellos). Tienen 2 servidores de CA, uno llamado Class 2 CA
y el otro llamado G2 CA
. Su Class 2 CA
firma todos SHA-1
certificados SHA-1
, mientras que la G2 CA
firma todos sus certificados SHA-2
. Aquí es donde radica el problema: GoDaddy no ha agregado su servidor G2 CA
más nuevo al almacén de confianza de java predeterminado, lo que hace que las instalaciones Java predeterminadas no confíen en su autoridad y, por lo tanto, no confían en su certificado encadenado. La solución temporal hasta que GoDaddy agregue el servidor de G2 CA
al almacén de confianza predeterminado es simplemente volver a activar su certificado usando SHA-1
como para obtener un certificado firmado por el servidor de Class 2 CA
. La nueva comercialización es gratuita para los clientes de GoDaddy hasta que su certificado caduque (obviamente).
El Sr. Fixer tiene razón. Instale el certificado "GoDaddy G1 a G2 Cross" en el archivo del paquete de certificados junto con el certificado intermedio. Esto permite que los certificados GoDaddy SHA-2 sean confiables para cualquier cliente que reconozca las raíces de SHA-1, incluido Java. Puede obtener este archivo de https://certs.godaddy.com/repository Una vez que esté instalado, Java creará una cadena de certificados de su certificado al "Certificado GoDaddy Secure Server (Certificado Intermedio)" a "GoDaddy G1 a G2". Certificado cruzado "a la raíz de GoDaddy SHA-1. También puede encontrar un archivo de paquete que contiene el certificado cruzado en nuestro repositorio. Una última nota sobre esta opción: las firmas en los certificados raíz no están marcadas, por lo que, aunque confíe en una raíz SHA-1, esto es tan seguro como una cadena completa de certificados SHA-2.
En el "Panel de control de Java" acabo de agregar el Certificado de raíz de GD a la "CA de sitio seguro" y ya no tengo el error de cert cuando uso Java. El certificado que agregué fue: Certificado de raíz de la autoridad de certificación Go Daddy Clase 2 - G2
Las respuestas del Sr. Fixer y Wayne Thayer han sido desestimadas, pero en realidad están abogando por las soluciones correctas. De hecho, Wayne Thayer lidera el negocio SSL de GoDaddy, por lo que probablemente lo sepa. Debe instalar el certificado "GoDaddy G1 a G2 Cross" en su cadena de certificados junto con el certificado intermedio.
La degradación a SHA1 no es una opción ideal, ya que está en desuso y le causará más trabajo en el futuro. Afortunadamente, GoDaddy ha proporcionado un certificado de cruce que resuelve este problema. Publicaron instrucciones, que Wayne ha duplicado, y están enterrados here .
Personalmente he probado esta solución con un certificado SHA2, y funciona bien. Es una solución muy superior frente a volver a introducir y degradar a SHA1. Cuando se requiere SHA2, esta opción no estará disponible de todos modos, y aún puede haber cadenas de herramientas Java sin el nuevo certificado.
Según el soporte de GoDaddy, a partir de julio de 2014, el certificado raíz correcto se incluyó en las versiones recientes de Java 8, y en septiembre de 2014, Wayne Thayer de GoDaddy here que el certificado "está programado para ser agregado a Java en los próximos meses". ". He revisado el archivo cacerts en Java 8 para Mac OS descargado desde aquí , y efectivamente contiene el certificado raíz SHA2.
Entonces, en lugar de que tu cadena se vea así:
- Autoridad de certificación Go Daddy Root - G2: (SHA-2) - Hash 47 BE AB C9 22 EA E8 0E 78 78 34 62 A7 9F 45 C2 54 FD E6 8B. Este es el certificado raíz que está integrado en algunos sistemas (por ejemplo, Chrome). SnakeDoc afirma que "no está integrado en Java, Windows CE, Microsoft Exchange y más plataformas".
- Go Daddy Secure Certificate Authority - G2: (SHA-2) - Hash 27 AC 93 69 FA F2 52 07 BB 26 27 CE FA CC BE 4E F9 C3 19 B8
- Su certificado SHA2
Debe tener un aspecto como este:
- Go Daddy Clase 2 Autoridad de certificación: (SHA-1) - Hash 27 96 BA E6 3F 18 01 E2 77 26 1B A0 D7 77 70 02 8F 20 EE E4. Este es el antiguo certificado raíz que está integrado en la mayoría de los sistemas, incluido Java.
- Autoridad de certificación Go Daddy Root - G2: (SHA-2) - Hash 34 0B 28 80 F4 46 FC C0 4E 59 ED 33 F5 2B 3D 08 D6 24 29 64. Este es el llamado "Certificado cruzado GoDaddy G1 a G2" .
- Go Daddy Secure Certificate Authority - G2: (SHA-2) - Hash 27 AC 93 69 FA F2 52 07 BB 26 27 CE FA CC BE 4E F9 C3 19 B8
- Su certificado SHA-2
Ver también - la publicación de mi blog que resume este problema con soluciones alternativas.
Los siguientes comentarios y el resultado de openssl s_client -connect the.server.name:587 -starttls smtp
.
En una cadena de certificados, la cert n debe emitirse por cert n + 1 en la lista: el emisor (i) de cert n debe ser el (los) sujeto (s) de cert n + 1.
0 s:/OU=Domain Control Validated/CN=smtp.somecompany.com
i:/C=US/ST=Arizona/L=Scottsdale/O=GoDaddy.com, Inc./OU=http://certs.godaddy.com/repository//CN=Go Daddy Secure Certificate Authority - G2
1 s:/C=US/ST=Arizona/L=Scottsdale/O=GoDaddy.com, Inc./OU=http://certs.godaddy.com/repository//CN=Go Daddy Secure Certificate Authority - G2
i:/C=US/ST=Arizona/L=Scottsdale/O=GoDaddy.com, Inc./CN=Go Daddy Root Certificate Authority - G2
2 s:/C=US/ST=Arizona/L=Scottsdale/O=GoDaddy.com, Inc./CN=Go Daddy Root Certificate Authority - G2
i:/C=US/ST=Arizona/L=Scottsdale/O=GoDaddy.com, Inc./CN=Go Daddy Root Certificate Authority - G2
3 s:/C=US/ST=Arizona/L=Scottsdale/O=GoDaddy.com, Inc./OU=http://certs.godaddy.com/repository//CN=Go Daddy Secure Certificate Authority - G2
i:/C=US/ST=Arizona/L=Scottsdale/O=GoDaddy.com, Inc./CN=Go Daddy Root Certificate Authority - G2
Aquí, cert 0 es emitido por cert 1 (fine), cert 1 es emitido por cert 2 (fine), cert 2 es autofirmado (también está bien, esta es la raíz CA).
Sin embargo, cert 3 no es emitido por cert 3. Cert 3 está fuera de lugar (y probablemente lo mismo que cert 1). Es probable que esto cause problemas, ya que esto hace que la cadena no sea válida.
Al menos debería eliminar el cert 3 de su configuración. Además, también puede eliminar cert 2, ya que no es necesario tener CA raíz (depende del cliente saberlo de todos modos).
Para que los certificados de Godaddy funcionen en Java con SHA2, necesitará usar su certificado cruzado en su cadena para encadenar la raíz G2 (SHA2) a la raíz G1 (SHA1) hasta que Java decida actualizar su repositorio. El paquete de Certificado Cruzado se puede descargar aquí:
https://certs.godaddy.com/anonymous/repository.pki
Paquetes de certificados GoDaddy - G2 con Cross to G1, incluye Root
[gd_bundle-g2-g1.crt][1]
Parece que su servidor de correo no está firmado por Go Daddy Class 2 Certification Authority
, pero en realidad está firmado por una de sus autoridades certificadoras intermedias. Deberá verificar esto usted mismo. Suponiendo que este es el caso ...
En teoría, su software debería funcionar, ya que el certificado intermedio está firmado por la autoridad de clase 2 y usted tiene la autoridad de clase 2 en el almacén de certificados JDK predeterminado. Sin embargo, descubrí que simplemente no funciona a menos que también agregue el certificado intermedio a su almacén de certificados. Aquí hay un enlace a una publicación de blog que describe una experiencia similar:
http://drcs.ca/blog/adding-godaddy-intermediate-certificates-to-java-jdk/
Aquí hay un enlace directo a más certificados intermedios GoDaddy: https://certs.godaddy.com/anonymous/repository.pki
No puedo aconsejar exactamente qué certificado debe agregar, depende de qué CA se utiliza en su servidor de correo.
[actualizar]
is there a way to do this programmically?
Tal vez. Depende de lo que quieras hacer. He utilizado la clase java.security.KeyStore
para actualizar automáticamente un keystore privado directamente desde el código Java sin usar keytool
. Es conceptualmente simple: cargue el almacén de claves de un archivo, lea el certificado nuevo, agréguelo al almacén de claves y luego escriba el almacén de claves en un archivo nuevo. Sin embargo, lleva un tiempo obtener los detalles correctos y puede que no valga la pena importar solo un certificado.
Aún así, es interesante intentarlo. Verifique KeyStore JavaDoc y lea los métodos load
, store
y setCertificateEntry
.
Si está utilizando las propiedades siguientes al enviar correo, entonces coméntelo. Esto funciona para mí Pero esto podría causar un problema de seguridad.
props.put("mail.smtp.starttls.enable","true");
si importa el paquete GoDady G2 al almacén de claves java resuelve el problema:
export JAVA_HOME=/usr/lib/jvm/java-8-oracle/
wget https://certs.godaddy.com/repository/gd_bundle-g2.crt
$JAVA_HOME/bin/keytool -import -alias root -file ./gd_bundle-g2.crt -storepass changeit -trustcacerts -keystore $JAVA_HOME/jre/lib/security/cacerts
UPDATE 1/26/2015 -- It appears the most recent JRE/JDK for Java 8 (update >= 31) and JRE/JDK for Java 7 now include the Godaddy G2 CA server in the default trust store. If possible, it''s urged you upgrade your JRE/JDK to the latest Java 8 update to resolve this issue.
ACTUALIZACIÓN 29/11/2014 - Esto sigue siendo un problema, y parece que Godaddy no se preocupa ni hará nada al respecto. Hay una publicación en el blog [here][1]
del Vicepresidente de Productos de Seguridad de Godaddy de hace varios meses que decía que había una solución y proporcionaba una solución temporal, pero a partir de hoy, nada ha cambiado. Es importante tener en cuenta que el servidor Godaddy''s G2 CA ha existido por un mínimo de 5 años, y en ese momento Godaddy no ha tomado las medidas adecuadas para resolver este problema conocido. La solución provista es solo eso, una solución alternativa, no una solución. Los usuarios de servicios de terceros no tienen control sobre cómo se instala el certificado en el servidor.
It seems users should avoid purchasing Godaddy SSL certs until they get serious about being a CA.
Aquí está la información de contacto de su equipo SSL si se siente inclinado a llamar:
GoDaddy SSL Team Support Number: 1-480-505-8852 -- Email: [email protected]
ACTUALIZACIÓN 17/09/2014 - Esto sigue siendo un problema, y parece que Godaddy no se preocupa ni hará nada al respecto. En noviembre, cuando Google derogue todos los certificados de SHA-1, se convertirá en un problema importante. Recomiendo encarecidamente a cualquiera que pueda contactar a Godaddy y señalarlos aquí.
~~~~
Mi mensaje / pregunta inicial fue sobre por qué mi cadena no funcionaba. Resultó obvio que tuve una mala configuración (que se solucionó rápidamente con algunos consejos de @Bruno y otros, gracias). Sin embargo, cuando mi cadena corregida todavía no funcionaba con Java, se hizo evidente que había un problema mucho más grande al acecho. Me tomó un tiempo, pero el problema es en realidad con GoDaddy.
En realidad, este es un problema de GoDaddy (he tenido largos correos de soporte con ellos).
Tienen 2 servidores de CA, uno llamado Class 2 CA
y el otro llamado G2 CA
. Su Class 2 CA
firma todos SHA-1
certificados SHA-1
, mientras que la G2 CA
firma todos sus certificados SHA-2
.
Aquí es donde radica el problema: GoDaddy no ha agregado su servidor G2 CA
más nuevo al Java truststore/keystore
Java predeterminado, lo que hace que las instalaciones Java predeterminadas no confíen en su autoridad y, por lo tanto, no confían en su certificado encadenado.
La solución temporal hasta que GoDaddy agregue el servidor de G2 CA
al almacén de claves / almacén de confianza predeterminado es simplemente volver a activar su certificado usando SHA-1
como-para obtener un certificado firmado por el servidor de Class 2 CA
. La nueva comercialización es gratuita para los clientes de GoDaddy hasta que su certificado caduque (obviamente).
Una vez que tenga un SHA-1
firmado por el servidor Class 2 CA
, su cadena de confianza debería funcionar como se espera y no se requieren importaciones y / o configuración de almacenes de confianza / almacén de claves personalizados.
No me alegra que deba usar un certificado "más débil" para que funcione correctamente, y las discusiones con GoDaddy a través del soporte de correo electrónico hasta ahora han indicado que no tienen planes actuales para agregar el servidor G2 CA
al almacén de confianza predeterminado. / keystore Supongo que hasta que lo agreguen, asegúrese de obtener un SHA-1
firmado del servidor Class 2 CA
SHA-1
si planea trabajar con Java.
Update - this "solution" is no longer valid (see my above accepted answer) - keeping this answer because it did help alleviate the problem so long as the side-effects are tolerable.
Ok, es posible que haya encontrado una solución alternativa para mi caso.
props.put("mail.smtp.ssl.trust", "smtp.somecompany.com");
Agregué esto a la construcción de mi sesión, y ahora funciona. Esto es una solución, no es una solución, ya que todavía no sé por qué mi certificado SSL Godaddy no es de confianza por defecto ... no es un certificado autofirmado.
Alguien por favor siéntase libre de tocar el timbre ya que realmente me gustaría entender este problema.