我有一个基于apache http客户端的http客户端,它似乎对ssl证书没有任何问题。我对全球认可的证书和带有自定义SSLSocketFactory的自签名证书进行了单元测试。
然而,当我在代理后面运行相同的代码时,它停止了工作。我不断得到这个可怕的例外:
javax.net.ssl.SSLPeerUnverifiedException: peer not authenticated
at com.sun.net.ssl.internal.ssl.SSLSessionImpl.getPeerCertificates(SSLSessionImpl.java:352)
at org.apache.http.conn.ssl.AbstractVerifier.verify(AbstractVerifier.java:128)
at org.apache.http.conn.ssl.SSLSocketFactory.connectSocket(SSLSocketFactory.java:572)
at org.apache.http.impl.conn.DefaultClientConnectionOperator.openConnection(DefaultClientConnectionOperator.java:180)
at org.apache.http.impl.conn.ManagedClientConnectionImpl.open(ManagedClientConnectionImpl.java:294)
at org.apache.http.impl.client.DefaultRequestDirector.tryConnect(DefaultRequestDirector.java:640)
at org.apache.http.impl.client.DefaultRequestDirector.execute(DefaultRequestDirector.java:479)
at org.apache.http.impl.client.AbstractHttpClient.execute(AbstractHttpClient.java:906)
at org.apache.http.impl.client.AbstractHttpClient.execute(AbstractHttpClient.java:805)
我将代码减少到最低限度,它仍然会抛出相同的异常。代码:
URI uri = new URI("https://www.google.com");
DefaultHttpClient client = new DefaultHttpClient();
client.getParams().setParameter(ConnRoutePNames.DEFAULT_PROXY,
new HttpHost("proxy.int", 8080, "https"));
HttpUriRequest request = new HttpGet(uri);
HttpResponse response = client.execute(request);
如果没有指定任何内容,我不确定它是否使用默认的ssl设置,所以我也明确地添加了它:
URI uri = new URI("https://www.google.com");
DefaultHttpClient client = new DefaultHttpClient();
client.getParams().setParameter(ConnRoutePNames.DEFAULT_PROXY,
new HttpHost("proxy.int", 8080, "https"));
client.getConnectionManager().getSchemeRegistry().register(
new Scheme("https", 443, SSLSocketFactory.getSystemSocketFactory()));
HttpUriRequest request = new HttpGet(uri);
HttpResponse response = client.execute(request);
我也尝试了getSocketFactory()(不完全确定与getSystemSocketFactory()有什么不同),但仍然是同样的错误。
修改:
代理具有可选的身份验证,我已尝试使用和不使用。使用以下代码设置身份验证信息:
client.getCredentialsProvider().setCredentials(
new AuthScope("proxy.int", 8080),
new UsernamePasswordCredentials("user", "password")
);
完全相同的错误。
答案 0 :(得分:7)
问题在于代理声明,我必须指定“http”而不是“https”:
client.getParams().setParameter(ConnRoutePNames.DEFAULT_PROXY,
new HttpHost("proxy.int", 8080, "http"));