Why don't proxyHost/proxyPort work when running my Java application?

匿名 (未验证) 提交于 2019-12-03 01:20:02

问题:

I have a java app that talks to some REST services, and I want to look at the HTTP traffic using Fiddler.

Fiddler acts as a proxy on localhost:8888, so the following Java VM options are supposed to configure java to use this proxy:

-Dhttp.proxyHost=localhost -Dhttp.proxyPort=8888 

However, if I pass these parameters when running the java app that I want to debug, I see no traffic in Fiddler.

I wrote a test Java app that simply performs an HTTP GET using HttpURLConnection.

I can view the HTTP traffic from this app in fiddler, if I specify the above-mentioned command-line parameters when debugging it from Eclipse.

What are the reasons that http.proxyHost/Port might not work for all java HTTP operations?

回答1:

You can tell HttpClient to honor the JDK system arguments using the below code (HttpClient 4.x).

public static final DefaultHttpClient HTTP = new DefaultHttpClient(); ProxySelectorRoutePlanner routePlanner = new ProxySelectorRoutePlanner(HTTP.getConnectionManager().getSchemeRegistry(), ProxySelector.getDefault()); HTTP.setRoutePlanner(routePlanner); 


回答2:

For 4.3.6 I used

HttpHost proxy = new HttpHost(System.getProperty("http.proxyHost"), Integer.parseInt(System.getProperty("http.proxyPort")), "http");//System.getProperty("http.proxyHost") DefaultRoutePlanner routePlanner = new DefaultProxyRoutePlanner(proxy); CloseableHttpClient httpClient = HttpClients.custom().setRoutePlanner(routePlanner).build(); 


回答3:

As mentioned above you need to do something like this:

 CloseableHttpClient httpClient = HttpClients.custom()    .setRoutePlanner(new SystemDefaultRoutePlanner(ProxySelector.getDefault()) 

But that will not be enough.

In TL;DR fashion - you also need all three of these system properties:

-Dhttp.proxyHost=localhost -Dhttp.proxyPort=8888 -Dhttp.nonProxyHosts=

The long answer can be found here:

As mentioned by Gerard Davison at the link above:

It can be very convenient when developing to server based application to run them using "localhost" in order to maintain consistency between developer machines. This is normally a good idea but there is a small case where this can cause problems.

Consider if you are running a local http proxy on your machine in order to capture your HTTP traffic. (Cough perhaps even the one in JDeveloper I work on). Then you might run into Java bug 6737819. Basically by default JDK 1.6 was hard coded not to send any request to localhost via a proxy which of course was a bit of a pain. Luckily a workaround was put in where you could put the string "~localhost" in your nonProxyHosts entry to turn of this feature:

java -client -classpath classes  -Dhttp.proxyHost=localhost  -Dhttp.proxyPort=8099 -Dhttp.nonProxyHosts=~localhost  -Dhttps.proxyHost=localhost  -Dhttps.proxyPort=8099 client.Example  

Now moving forward to JDK 1.7 this workaround no longer works; but you need to take care to define nonProxyHosts as an empty string:

java -client -classpath classes  -Dhttp.proxyHost=localhost  -Dhttp.proxyPort=8099  -Dhttp.nonProxyHosts=  -Dhttps.proxyHost=localhost  -Dhttps.proxyPort=8099 client.Example   

If you define this any anything other than an empty string the DefaultProxySelector though beware because internally it will append / or use the http.nonProxyHosts value from ../jre/lib/net.properties".

Just a minor complication that is not obvious from the published API.



回答4:

With Apache httpclient 4.3.6, it seems that you should use SystemDefaultRoutePlanner.

SystemDefaultRoutePlanner routePlanner = new SystemDefaultRoutePlanner(null); CloseableHttpClient httpClient = HttpClientBuilder.create()   .setRoutePlanner(routePlanner)   .build(); 

This will pick up the proxy settings from system properties http.proxyHost and http.proxyPort, and will use the current settings of those values each time a new http request is sent.



标签
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!