【发布时间】:2018-07-10 15:30:05
【问题描述】:
我正在尝试使用 Socks5 代理服务器来请求在我的 Java 应用程序中需要代理的特定目标(主机)。我正在使用 Apache Http 库(v. 4.5.4)。我有许多不需要代理的其他目标,因此为整个应用程序全局设置代理对我来说不是一个选择。所以我为HttpClient 的某个实例设置了代理。代理需要登录并通过身份验证。
我的解决方案是基于此question,另外添加documentation 中所述的身份验证参数。
这是我的代码:
private void sendSocks5Request(StringEntity requestEntity) throws Exception {
Registry<ConnectionSocketFactory> reg = RegistryBuilder.<ConnectionSocketFactory>create()
.register("http", PlainConnectionSocketFactory.INSTANCE)
.register("https", new MyConnectionSocketFactory(SSLContexts.createSystemDefault()))
.build();
PoolingHttpClientConnectionManager cm = new PoolingHttpClientConnectionManager(reg);
Credentials credentials = new UsernamePasswordCredentials("proxy_user","proxy_pass");
AuthScope authScope = new AuthScope("my.proxy.com", 1080);
CredentialsProvider credsProvider = new BasicCredentialsProvider();
credsProvider.setCredentials(authScope, credentials);
CloseableHttpClient httpclient = HttpClients.custom()
.setConnectionManager(cm)
.setDefaultCredentialsProvider(credsProvider)
.build();
try {
InetSocketAddress socksaddr = new InetSocketAddress("my.proxy.com", 1080);
HttpClientContext context = HttpClientContext.create();
context.setAttribute("socks.address", socksaddr);
HttpHost target = new HttpHost("api.telegram.org", 80, "https");
HttpPost request = new HttpPost("/bot<bot_token_here>");
request.setEntity(requestEntity);
System.out.println("Executing request " + request + " to " + target + " via SOCKS proxy " + socksaddr);
CloseableHttpResponse response = httpclient.execute(target, request, context);
try {
System.out.println("----------------------------------------");
System.out.println(response.getStatusLine());
EntityUtils.consume(response.getEntity());
} catch (Exception ex) {
ex.getMessage();
} finally {
response.close();
}
} catch (Exception ex) {
ex.getMessage();
} finally {
httpclient.close();
}
}
代理似乎工作,但我得到一个Authentication failed 错误。代理服务器本身的日志显示,提供的身份验证不包含proxy_user 用户,而是我机器的系统用户。所以看起来 HttpClient 忽略了提供的凭据并从系统中获取它。
我做错了什么?
【问题讨论】:
-
我们有同样的问题,我们使用的代理不需要身份验证,但是因为我们的 java 代码本质上是发送系统用户(这实际上是一个安全问题,因为它提供了目标系统不提供的信息需要!!!)代理会抛出一个错误,导致整个通信失败。你有办法吗?看来这个问题是唯一解决这个问题的!
标签: java authentication proxy apache-httpclient-4.x socks