본문 바로가기
이슈

SSL 이슈 : unable to find valid certification path to requested target

by _Nate 2023. 5. 27.
반응형

1. JAVA가 client일 때 외부 사이트와 https통신을 하는 과정에 아래와 같이 Exception 발생

sun.security.provider.certpath.SunCertPathBuilderException: unable to find valid certification path to requested target

 

 

2. Client와 Server간 인증서 전달 방법

1) Client가 서버로 https요청을 하면 서버는 CA에서 제공하는 개인키로 암호화된 SSL인증서를 client에거 전달함
2) Client는 전달받은 인증서를 CA에서 제공하는 공개키로 복호화 시도함
3) Client에 암호화된 인증서를 복호화할 CA 공개키가 없는 경우 복호화 실패
반응형

3. 발급받은 인증서의 CA Root확인

  • Issuer(발급자)의 CN값 확인
[root@localhost ~]# openssl x509 -in ./DigiCertCA.cer -noout -text
Certificate:
...
        Issuer: C = US, O = DigiCert Inc, OU = www.digicert.com, CN = DigiCert Global Root G2

 

4. 사용하는 JAVA가 보유한 CA루트값 리스트 확인

[root@localhost ~]# keytool -keystore $JAVA_HOME/jre/lib/security/cacerts -storepass changeit -list -v
  • JAVA가 보유한 CA루트값 중 발급받은 인증서의 CA Root가 존재해야 함
  • 존재하지 않을 경우 'unable to find valid certification path to requested target' 발생

 

5. 해결방법

1) Client가 가지고 있는 CA Root와 동일한 인증서 발급 요청
2) Client의 버전을 업그레이드
3) Client의 CA Root 저장소에 발급받은 인증서의 CA Root를 추가

 

6. 테스트

  • java의 http.client를 통해 https 통신 시도
[root@localhost ~]# java HttpTest
Exception in thread "main" javax.net.ssl.SSLHandshakeException: sun.security.validator.ValidatorException: PKIX path building failed: sun.security.provider.certpath.SunCertPathBuilderException: unable to find valid certification path to requested target
        at com.sun.net.ssl.internal.ssl.Alerts.getSSLException(Alerts.java:174)
        at com.sun.net.ssl.internal.ssl.SSLSocketImpl.fatal(SSLSocketImpl.java:1747)
        at com.sun.net.ssl.internal.ssl.Handshaker.fatalSE(Handshaker.java:241)
        at com.sun.net.ssl.internal.ssl.Handshaker.fatalSE(Handshaker.java:235)
        at com.sun.net.ssl.internal.ssl.ClientHandshaker.serverCertificate(ClientHandshaker.java:1209)
(....)
        at org.apache.http.impl.client.CloseableHttpClient.execute(CloseableHttpClient.java:56)
        at HttpTest.main(HttpTest.java:22)
Caused by: sun.security.validator.ValidatorException: PKIX path building failed: sun.security.provider.certpath.SunCertPathBuilderException: unable to find valid certification path to requested target
        at sun.security.validator.PKIXValidator.doBuild(PKIXValidator.java:323)
        at sun.security.validator.PKIXValidator.engineValidate(PKIXValidator.java:217)
        at sun.security.validator.Validator.validate(Validator.java:218)
(....)
Caused by: sun.security.provider.certpath.SunCertPathBuilderException: unable to find valid certification path to requested target
       at sun.security.provider.certpath.SunCertPathBuilder.engineBuild(SunCertPathBuilder.java:174)
       at java.security.cert.CertPathBuilder.build(CertPathBuilder.java:238)
       at sun.security.validator.PKIXValidator.doBuild(PKIXValidator.java:318)
  • unable to find valid certification path to requested target 발생하며 통신 실패

 

  • 서버의 인증서 정보 확인결과 CA Root값이 DigiCert Global Root G2인것을 확인
  • Client에 존재하는 CA Root 리스트 확인
[root@localhost ~]# keytool -keystore ./cacerts -storepass changeit -list -v | grep DigiCert
Owner: CN=DigiCert Assured ID Root CA, OU=www.digicert.com, O=DigiCert Inc, C=US
Issuer: CN=DigiCert Assured ID Root CA, OU=www.digicert.com, O=DigiCert Inc, C=US
Owner: CN=DigiCert High Assurance EV Root CA, OU=www.digicert.com, O=DigiCert Inc, C=US
Issuer: CN=DigiCert High Assurance EV Root CA, OU=www.digicert.com, O=DigiCert Inc, C=US
Owner: CN=DigiCert Global Root CA, OU=www.digicert.com, O=DigiCert Inc, C=US
Issuer: CN=DigiCert Global Root CA, OU=www.digicert.com, O=DigiCert Inc, C=US
  • DigiCert Global Root G2 가 없음

 

  • Client의 CA Root 저장소(cacerts)에 DigiCert Global Root G2 추가
[root@localhost ~]# keytool -importcert -alias test -keystore ./cacerts -file ~/DigiCertCA.cer
Enter keystore password:
Owner: CN=Thawte TLS RSA CA G1, OU=www.digicert.com, O=DigiCert Inc, C=US
Issuer: CN=DigiCert Global Root G2, OU=www.digicert.com, O=DigiCert Inc, C=US
Valid from: Thu Nov 02 12:24:25 UTC 2017 until: Tue Nov 02 12:24:25 UTC 2027
Certificate fingerprints:
....
]

Trust this certificate? [no]:  y
Certificate was added to keystore

 

  • Client의 CA 저장소 재 확인
[root@localhost ~]# keytool -keystore ./cacerts -storepass changeit -list -v | grep DigiCert
Owner: CN=DigiCert Assured ID Root CA, OU=www.digicert.com, O=DigiCert Inc, C=US
Issuer: CN=DigiCert Assured ID Root CA, OU=www.digicert.com, O=DigiCert Inc, C=US
Owner: CN=DigiCert High Assurance EV Root CA, OU=www.digicert.com, O=DigiCert Inc, C=US
Issuer: CN=DigiCert High Assurance EV Root CA, OU=www.digicert.com, O=DigiCert Inc, C=US
Owner: CN=DigiCert Global Root CA, OU=www.digicert.com, O=DigiCert Inc, C=US
Issuer: CN=DigiCert Global Root CA, OU=www.digicert.com, O=DigiCert Inc, C=US
Owner: CN=DigiCert Global Root G2, OU=www.digicert.com, O=DigiCert Inc, C=US
Issuer: CN=DigiCert Global Root G2, OU=www.digicert.com, O=DigiCert Inc, C=US
  • DigiCert Global Root G2가 추가됨

 

  • java application 재호출 -> 정상 호출 확인

 

7. 관련 이슈

[인증서 정보]
루트 :  DigiCert Global Root CA ➜ DigiCert Global Root G2
중개 :  
   RapidSSL Global TLS RSA4096 SHA256 2022 CA1 ➜ RapidSSL TLS RSA CA G1
   GeoTrust Global TLS RSA4096 SHA256 2022 CA1 ➜ GeoTrust TLS RSA CA G1
   Thawte RSA CA 2018 ➜ Thawte TLS RSA CA G1
   DigiCert TLS RSA SHA256 2020 CA1 ➜ DigiCert Global G2 TLS RSA SHA256 2020 CA1
  • DigiCert Global Root G2버전의 Client별 최소 요구 버전 확인

  • 해당 버전으로 변경이 불가한 경우 위의 테스트 내용과 같이 CA 저장소에 CA Root 정보 추가 필요

 

반응형