1

我正在尝试https通过我的 android 应用程序访问一个 url 并获取javax.net.ssl.SSLHandshakeException: java.security.cert.CertPathValidatorException: Trust anchor for certification path not found.

例外是:

06-10 14:18:37.083: W/System.err(28459): javax.net.ssl.SSLHandshakeException: java.security.cert.CertPathValidatorException: Trust anchor for certification path not found.
06-10 14:18:37.083: W/System.err(28459):    at org.apache.harmony.xnet.provider.jsse.OpenSSLSocketImpl.startHandshake(OpenSSLSocketImpl.java:399)
06-10 14:18:37.083: W/System.err(28459):    at libcore.net.http.HttpConnection.setupSecureSocket(HttpConnection.java:211)
06-10 14:18:37.083: W/System.err(28459):    at libcore.net.http.HttpsURLConnectionImpl$HttpsEngine.makeSslConnection(HttpsURLConnectionImpl.java:478)
06-10 14:18:37.083: W/System.err(28459):    at libcore.net.http.HttpsURLConnectionImpl$HttpsEngine.connect(HttpsURLConnectionImpl.java:433)
06-10 14:18:37.083: W/System.err(28459):    at libcore.net.http.HttpEngine.sendSocketRequest(HttpEngine.java:289)
06-10 14:18:37.083: W/System.err(28459):    at libcore.net.http.HttpEngine.sendRequest(HttpEngine.java:239)
06-10 14:18:37.093: W/System.err(28459):    at libcore.net.http.HttpURLConnectionImpl.connect(HttpURLConnectionImpl.java:80)
06-10 14:18:37.093: W/System.err(28459):    at libcore.net.http.HttpsURLConnectionImpl.connect(HttpsURLConnectionImpl.java:165)
06-10 14:18:37.093: W/System.err(28459):    at com.virinchi.activity.LoginActivity$SignedDownloadManager.doInBackground(LoginActivity.java:542)
06-10 14:18:37.093: W/System.err(28459):    at com.virinchi.activity.LoginActivity$SignedDownloadManager.doInBackground(LoginActivity.java:1)
06-10 14:18:37.093: W/System.err(28459):    at android.os.AsyncTask$2.call(AsyncTask.java:287)
06-10 14:18:37.093: W/System.err(28459):    at java.util.concurrent.FutureTask$Sync.innerRun(FutureTask.java:305)
06-10 14:18:37.093: W/System.err(28459):    at java.util.concurrent.FutureTask.run(FutureTask.java:137)
06-10 14:18:37.093: W/System.err(28459):    at android.os.AsyncTask$SerialExecutor$1.run(AsyncTask.java:230)
06-10 14:18:37.093: W/System.err(28459):    at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1076)
06-10 14:18:37.093: W/System.err(28459):    at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:569)
06-10 14:18:37.093: W/System.err(28459):    at java.lang.Thread.run(Thread.java:856)
06-10 14:18:37.093: W/System.err(28459): Caused by: java.security.cert.CertificateException: java.security.cert.CertPathValidatorException: Trust anchor for certification path not found.
06-10 14:18:37.093: W/System.err(28459):    at org.apache.harmony.xnet.provider.jsse.TrustManagerImpl.checkTrusted(TrustManagerImpl.java:192)
06-10 14:18:37.093: W/System.err(28459):    at org.apache.harmony.xnet.provider.jsse.TrustManagerImpl.checkServerTrusted(TrustManagerImpl.java:163)
06-10 14:18:37.093: W/System.err(28459):    at org.apache.harmony.xnet.provider.jsse.OpenSSLSocketImpl.verifyCertificateChain(OpenSSLSocketImpl.java:598)
06-10 14:18:37.093: W/System.err(28459):    at org.apache.harmony.xnet.provider.jsse.NativeCrypto.SSL_do_handshake(Native Method)
06-10 14:18:37.093: W/System.err(28459):    at org.apache.harmony.xnet.provider.jsse.OpenSSLSocketImpl.startHandshake(OpenSSLSocketImpl.java:396)
06-10 14:18:37.093: W/System.err(28459):    ... 16 more
06-10 14:18:37.093: W/System.err(28459): Caused by: java.security.cert.CertPathValidatorException: Trust anchor for certification path not found.
06-10 14:18:37.103: W/System.err(28459):    ... 21 more
06-10 14:18:37.133: W/System.err(28459): javax.net.ssl.SSLHandshakeException: java.security.cert.CertPathValidatorException: Trust anchor for certification path not found.
06-10 14:18:37.133: W/System.err(28459):    at org.apache.harmony.xnet.provider.jsse.OpenSSLSocketImpl.startHandshake(OpenSSLSocketImpl.java:399)
06-10 14:18:37.133: W/System.err(28459):    at libcore.net.http.HttpConnection.setupSecureSocket(HttpConnection.java:211)
06-10 14:18:37.133: W/System.err(28459):    at libcore.net.http.HttpsURLConnectionImpl$HttpsEngine.makeSslConnection(HttpsURLConnectionImpl.java:478)
06-10 14:18:37.133: W/System.err(28459):    at libcore.net.http.HttpsURLConnectionImpl$HttpsEngine.connect(HttpsURLConnectionImpl.java:433)
06-10 14:18:37.133: W/System.err(28459):    at libcore.net.http.HttpEngine.sendSocketRequest(HttpEngine.java:289)
06-10 14:18:37.133: W/System.err(28459):    at libcore.net.http.HttpEngine.sendRequest(HttpEngine.java:239)
06-10 14:18:37.133: W/System.err(28459):    at libcore.net.http.HttpURLConnectionImpl.connect(HttpURLConnectionImpl.java:80)
06-10 14:18:37.133: W/System.err(28459):    at libcore.net.http.HttpsURLConnectionImpl.connect(HttpsURLConnectionImpl.java:165)
06-10 14:18:37.133: W/System.err(28459):    at com.virinchi.activity.LoginActivity$UnSignedDownloadManager.doInBackground(LoginActivity.java:644)
06-10 14:18:37.133: W/System.err(28459):    at com.virinchi.activity.LoginActivity$UnSignedDownloadManager.doInBackground(LoginActivity.java:1)
06-10 14:18:37.133: W/System.err(28459):    at android.os.AsyncTask$2.call(AsyncTask.java:287)
06-10 14:18:37.143: W/System.err(28459):    at java.util.concurrent.FutureTask$Sync.innerRun(FutureTask.java:305)
06-10 14:18:37.143: W/System.err(28459):    at java.util.concurrent.FutureTask.run(FutureTask.java:137)
06-10 14:18:37.143: W/System.err(28459):    at android.os.AsyncTask$SerialExecutor$1.run(AsyncTask.java:230)
06-10 14:18:37.143: W/System.err(28459):    at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1076)
06-10 14:18:37.143: W/System.err(28459):    at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:569)
06-10 14:18:37.143: W/System.err(28459):    at java.lang.Thread.run(Thread.java:856)
06-10 14:18:37.143: W/System.err(28459): Caused by: java.security.cert.CertificateException: java.security.cert.CertPathValidatorException: Trust anchor for certification path not found.
06-10 14:18:37.143: W/System.err(28459):    at org.apache.harmony.xnet.provider.jsse.TrustManagerImpl.checkTrusted(TrustManagerImpl.java:192)
06-10 14:18:37.143: W/System.err(28459):    at org.apache.harmony.xnet.provider.jsse.TrustManagerImpl.checkServerTrusted(TrustManagerImpl.java:163)
06-10 14:18:37.143: W/System.err(28459):    at org.apache.harmony.xnet.provider.jsse.OpenSSLSocketImpl.verifyCertificateChain(OpenSSLSocketImpl.java:598)
06-10 14:18:37.143: W/System.err(28459):    at org.apache.harmony.xnet.provider.jsse.NativeCrypto.SSL_do_handshake(Native Method)
06-10 14:18:37.143: W/System.err(28459):    at org.apache.harmony.xnet.provider.jsse.OpenSSLSocketImpl.startHandshake(OpenSSLSocketImpl.java:396)
06-10 14:18:37.143: W/System.err(28459):    ... 16 more
06-10 14:18:37.153: W/System.err(28459): Caused by: java.security.cert.CertPathValidatorException: Trust anchor for certification path not found.
06-10 14:18:37.153: W/System.err(28459):    ... 21 more

这是允许httpsurl 的以下代码:

private HttpClient sslClient(HttpClient client) {
    try {
        X509TrustManager tm = new X509TrustManager() { 
            public void checkClientTrusted(X509Certificate[] xcs, String string) throws CertificateException {
            }

            public void checkServerTrusted(X509Certificate[] xcs, String string) throws CertificateException {
            }

            public X509Certificate[] getAcceptedIssuers() {
                return null;
            }
        };
        SSLContext ctx = SSLContext.getInstance("TLS");
        ctx.init(null, new TrustManager[]{tm}, null);
        SSLSocketFactory ssf = new SSLFactory(ctx);
        ssf.setHostnameVerifier(SSLSocketFactory.ALLOW_ALL_HOSTNAME_VERIFIER);
        ClientConnectionManager ccm = client.getConnectionManager();
        SchemeRegistry sr = ccm.getSchemeRegistry();
        sr.register(new Scheme("https", ssf, 443));
        return new DefaultHttpClient(ccm, client.getParams());
    } catch (Exception ex) {
        return null;
    }
}

我在我的类的doInBackground方法中调用上面的代码。AsyncTask代码是:

 @Override
    protected Header[] doInBackground(String... params) {
        try {
            HttpClient httpClient = new DefaultHttpClient();
            httpClient =  sslClient(httpClient);
            HttpPost httpPost = new HttpPost(params[1]);

            ArrayList<NameValuePair> nameValuePair = new ArrayList<NameValuePair>();
            nameValuePair.add(new BasicNameValuePair("ssn", params[0]));
            nameValuePair.add(new BasicNameValuePair("macAddr", params[2]));
            httpPost.setEntity(new UrlEncodedFormEntity(nameValuePair,
                    "UTF-8"));
            HttpResponse httpResponse = httpClient.execute(httpPost);
            HttpEntity httpEntity = httpResponse.getEntity();
            response = EntityUtils.toString(httpEntity);
            allHeaders = httpResponse.getAllHeaders();

        } catch (Exception ex) {

            ex.printStackTrace();

        }
        return allHeaders;
    }

这是我的 SSLFactory 类:

public class SSLFactory extends SSLSocketFactory {
SSLContext sslContext = SSLContext.getInstance("TLS");

public SSLFactory(KeyStore truststore) throws NoSuchAlgorithmException, KeyManagementException, KeyStoreException, UnrecoverableKeyException {
    super(truststore);

    X509TrustManager tm = new X509TrustManager() {
        public void checkClientTrusted(X509Certificate[] chain, String authType) throws CertificateException {
        }

        public void checkServerTrusted(X509Certificate[] chain, String authType) throws CertificateException {
        }

        public X509Certificate[] getAcceptedIssuers() {
            return null;
        }
    };

    sslContext.init(null, new X509TrustManager[] { tm }, null);
}

public SSLFactory(SSLContext context) throws KeyManagementException, NoSuchAlgorithmException, KeyStoreException, UnrecoverableKeyException {
   super(null);
   sslContext = context;
}

@Override
public Socket createSocket(Socket socket, String host, int port, boolean autoClose) throws IOException, UnknownHostException {
    return sslContext.getSocketFactory().createSocket(socket, host, port, autoClose);
}

@Override
public Socket createSocket() throws IOException {
    return sslContext.getSocketFactory().createSocket();
}

public static HttpClient sslClient(HttpClient client) {
    try {
        X509TrustManager tm = new X509TrustManager() { 
            public void checkClientTrusted(X509Certificate[] xcs, String string) throws CertificateException {
            }

            public void checkServerTrusted(X509Certificate[] xcs, String string) throws CertificateException {
            }

            public X509Certificate[] getAcceptedIssuers() {
                return null;
            }
        };
        SSLContext ctx = SSLContext.getInstance("TLS");
        ctx.init(null, new TrustManager[]{tm}, null);
        SSLSocketFactory ssf = new SSLFactory(ctx);
        ssf.setHostnameVerifier(SSLSocketFactory.ALLOW_ALL_HOSTNAME_VERIFIER);
        ClientConnectionManager ccm = client.getConnectionManager();
        SchemeRegistry sr = ccm.getSchemeRegistry();
        sr.register(new Scheme("https", ssf, 443));
        return new DefaultHttpClient(ccm, client.getParams());
    } catch (Exception ex) {
        return null;
    }
}
 }
4

1 回答 1

1

首先你应该在你的服务器(https://xxx.yyy.zzzz)中配置 SSL 证书,然后使用 https api 然后你得到正确的响应而不是这个异常

于 2014-06-10T09:34:25.597 回答