简体   繁体   English

OAuth 中的 PKIX 路径构建失败 Java 中的身份验证

[英]PKIX path building failed in OAuth Authentication in Java

I am trying to Authenticate in discogs:我正在尝试在 discogs 中进行身份验证:

https://www.discogs.com/developers/#page:authentication,header:authentication-oauth-flow https://www.discogs.com/developers/#page:authentication,header:authentication-oauth-flow

on the Point 2: SEND A GET REQUEST TO THE DISCOGS REQUEST TOKEN URL, I get this:关于第 2 点:向 DISCOGS 请求令牌 URL 发送 GET 请求,我明白了:

oauth_token=tnMYYwCBsvoecGyBsANXyVKQtICTdDnnzRPeGUfa
oauth_token_secret=xwHpnTRYNJIpdkkTJLMsfXECdHgXeQUrDjzmktPw
oauth_callback_confirmed=true

on the POINT 3: REDIRECT YOUR USER TO THE DISCOGS AUTHORIZE PAGE,关于第 3 点:将您的用户重定向到 DISCOGS 授权页面,

I've created this piece of code:我创建了这段代码:

private static void redirectUserToAuthorizePage(String consumerKey) throws IOException {

    String yourUrl = "https://discogs.com/oauth/authorize?oauth_token=" + consumerKey;
    URL url = new URL(yourUrl);
    HttpURLConnection conn = (HttpURLConnection) url.openConnection();
    conn.setDoOutput(true);
    conn.setRequestMethod("GET");

    int statusCode = conn.getResponseCode();
    System.out.println("Status Code: " + statusCode);

    conn.disconnect();

}

But I got this error:但我得到了这个错误:

but I get this error:但我收到此错误:

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 sun.security.ssl.Alerts.getSSLException(Alerts.java:192)
    at sun.security.ssl.SSLSocketImpl.fatal(SSLSocketImpl.java:1949)
    at sun.security.ssl.Handshaker.fatalSE(Handshaker.java:302)
    at sun.security.ssl.Handshaker.fatalSE(Handshaker.java:296)
    at sun.security.ssl.ClientHandshaker.serverCertificate(ClientHandshaker.java:1509)
    at sun.security.ssl.ClientHandshaker.processMessage(ClientHandshaker.java:216)
    at sun.security.ssl.Handshaker.processLoop(Handshaker.java:979)
    at sun.security.ssl.Handshaker.process_record(Handshaker.java:914)
    at sun.security.ssl.SSLSocketImpl.readRecord(SSLSocketImpl.java:1062)
    at sun.security.ssl.SSLSocketImpl.performInitialHandshake(SSLSocketImpl.java:1375)
    at sun.security.ssl.SSLSocketImpl.startHandshake(SSLSocketImpl.java:1403)
    at sun.security.ssl.SSLSocketImpl.startHandshake(SSLSocketImpl.java:1387)
    at sun.net.www.protocol.https.HttpsClient.afterConnect(HttpsClient.java:559)
    at sun.net.www.protocol.https.AbstractDelegateHttpsURLConnection.connect(AbstractDelegateHttpsURLConnection.java:185)
    at sun.net.www.protocol.http.HttpURLConnection.getInputStream0(HttpURLConnection.java:1513)
    at sun.net.www.protocol.http.HttpURLConnection.getInputStream(HttpURLConnection.java:1441)
    at java.net.HttpURLConnection.getResponseCode(HttpURLConnection.java:480)
    at sun.net.www.protocol.https.HttpsURLConnectionImpl.getResponseCode(HttpsURLConnectionImpl.java:338)

The error provided indicates that your application is unable to establish a SSL secure communication with the remote server, discogs.com , because it is unable to find a valid certificate for that server among the ones configured to trust.提供的错误表明您的应用程序无法与远程服务器discogs.com建立 SSL 安全通信,因为它无法在配置为信任的服务器中找到该服务器的有效证书。

Under the hood, HttpURLConnection will use Java Secure Socket Extension for establishing secure SSL communications.在后台, HttpURLConnection将使用Java 安全套接字扩展来建立安全的 SSL 通信。

In order to solve the problem you have several options, mainly:为了解决这个问题,你有几个选择,主要是:

  • Run your application with the javax.net.ssl.trustStore and javax.net.ssl.trustStorePassword system properties pointing to a keystore and respectively password that contains your server certificates.使用指向包含服务器证书的密钥库和密码的javax.net.ssl.trustStorejavax.net.ssl.trustStorePassword系统属性运行您的应用程序。
  • Include the server certificate in a trusted, default, keystore, one of:将服务器证书包含在受信任的默认密钥库中,其中之一是:
    • <java-home>/lib/security/jssecacerts
    • <java-home>/lib/security/cacerts

No matter the chosen mechanism, be sure that the desired keystore contains all the necessary certificates to trust the remote server, not only the SSL certificate itself, but all the certificates in the certificate chain.无论选择何种机制,请确保所需的密钥库包含信任远程服务器所需的所有证书,不仅是 SSL 证书本身,还包括证书链中的所有证书。

openssl provides an useful command that allows you to obtain all the certificates used in the SSL connection. openssl提供了一个有用的命令,允许您获取 SSL 连接中使用的所有证书。 In this case, it will provide the following information, among other:在这种情况下,它将提供以下信息,其中包括:

depth=0 O = Acme Co, CN = Kubernetes Ingress Controller Fake Certificate
verify error:num=20:unable to get local issuer certificate
verify return:1
depth=0 O = Acme Co, CN = Kubernetes Ingress Controller Fake Certificate
verify error:num=21:unable to verify the first certificate
verify return:1
---
Certificate chain
 0 s:/O=Acme Co/CN=Kubernetes Ingress Controller Fake Certificate
   i:/O=Acme Co/CN=Kubernetes Ingress Controller Fake Certificate
-----BEGIN CERTIFICATE-----
MIIDcDCCAligAwIBAgIRALyiewLACTbxSO/mUgPt2z8wDQYJKoZIhvcNAQELBQAw
SzEQMA4GA1UEChMHQWNtZSBDbzE3MDUGA1UEAxMuS3ViZXJuZXRlcyBJbmdyZXNz
IENvbnRyb2xsZXIgRmFrZSBDZXJ0aWZpY2F0ZTAeFw0yMTAzMTYyMjQ5MDVaFw0y
MjAzMTYyMjQ5MDVaMEsxEDAOBgNVBAoTB0FjbWUgQ28xNzA1BgNVBAMTLkt1YmVy
bmV0ZXMgSW5ncmVzcyBDb250cm9sbGVyIEZha2UgQ2VydGlmaWNhdGUwggEiMA0G
CSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQDxBj7SvSJpus5+2s4HLhheJhmKEmcV
MTFIVf3xRDfGpVFeYKAc/o8oB3/OXrqr16kuv2g+bE2d59qVri1uTXX/CRHM6G0E
St/gEdUsGiO1e3VueYGkdgr//s7idEMD0tBHp9ITiR0XUFK75YdWCT6H24fetNzp
bOSMImEeSQsRexKqwcCvM6l4rNshJQ1BVD7NOYPBO9BJuEKU0wCd8yDF20Ig6Qwh
D8B6kRIfNIR1jaQbXGwsvowx4ZHtE4ETd5ftPvKFLfjTMRNFOenJMOeA9te3f2vA
f4jm8furOytI7+sQhZqstxbwPV9OI96rilq4P+ZjP3CW9bfubdyE8ccHAgMBAAGj
TzBNMA4GA1UdDwEB/wQEAwIFoDATBgNVHSUEDDAKBggrBgEFBQcDATAMBgNVHRMB
Af8EAjAAMBgGA1UdEQQRMA+CDWluZ3Jlc3MubG9jYWwwDQYJKoZIhvcNAQELBQAD
ggEBADFd9W49IsGKTm6WBSsSPLuKn1NFlQmfuRljcZyB01seN7N8fvX4OG/fD+/A
g1nogwDbTl3g1AAyiU6iCKerZevolS2akLdbKwxg/olFRjgwdTN5668Dbz4o3MVY
21AJJ9qO14Oxdu5x+3VhMnsuQdcOzdpwVPmNWIOGQMPD+sOZ8d1hqFp6+3gFQpIL
4kEs2RhjZqwySYoQmBnURx8kbyrs3s/sH06v+CzJwVomf7amOaywJ/VuxmkF9JPp
pxxmlHfbSzlWZGRC4K0ij1+91r6EALVUGgonQGY3FsN2+JTTfg8J9FGqvjb7F+BO
PMPqU/pmCW5h8ej8eyNflagzLFE=
-----END CERTIFICATE-----
---
Server certificate
subject=/O=Acme Co/CN=Kubernetes Ingress Controller Fake Certificate
issuer=/O=Acme Co/CN=Kubernetes Ingress Controller Fake Certificate
---

In this case, it seems that the server is using a self-signed certificate to identify itself.在这种情况下,服务器似乎正在使用自签名证书来标识自己。 You new to configure Java to trust that certificate.您新配置 Java 以信任该证书。

Copy and paste the certificate text outputted in the command, including —–BEGIN CERTIFICATE—– and —–END CERTIFICATE—– , and save to a new file, discogs.pem , for example.复制并粘贴命令中输出的证书文本,包括—–BEGIN CERTIFICATE—–—–END CERTIFICATE—– ,并保存到一个新文件,例如discogs.pem

In order to be imported in a Java keystore, it should be converted to DER format first.为了在 Java 密钥库中导入,应首先将其转换为 DER 格式。 You can do that with openssl as well:您也可以使用openssl来做到这一点:

openssl x509 -outform der -in discogs.pem -out discogs.der

Then, import the certificate in a keystore.然后,将证书导入密钥库。 As indicated, you can import it in the default JVM kystore, or in a new one.如图所示,您可以将其导入默认的 JVM kystore 或新的。 Let's consider the later case and create a new keystore named, for example, discogs :让我们考虑后一种情况并创建一个名为discogs的新密钥库:

keytool -import -keystore discogs -file discogs.der

Provide a password of your convenience, let's assume changeme for example.提供您方便的密码,我们假设changeme为例。

Now, run the application with the above-mentioned system properties:现在,使用上述系统属性运行应用程序:

java -Djavax.net.ssl.trustStore=discogs \
     -Djavax.net.ssl.trustStorePassword=changeme \
     your.Application

If necessary, in order to troubleshoot the problem , you can use the javax.net.debug system property with an appropriate value, all or ssl :如有必要,为了解决问题,您可以使用具有适当值的javax.net.debug系统属性allssl

java -Djavax.net.debug=ssl \
     -Djavax.net.ssl.trustStore=discogs \
     -Djavax.net.ssl.trustStorePassword=password \
     your.Application

Please, consider review this related SO question , it may be of help.请考虑查看这个相关的 SO question ,它可能会有所帮助。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM