如何在java.net.URLConnection上指定本地地址?

我的Tomcat实例正在侦听多个IP地址,但我想控制打开URLConnection时使用的源IP地址。

我怎么指定这个?

这应该是诀窍:

 URL url = new URL(yourUrlHere); Proxy proxy = new Proxy(Proxy.Type.DIRECT, new InetSocketAddress( InetAddress.getByAddress( new byte[]{your, ip, interface, here}), yourTcpPortHere)); URLConnection conn = url.openConnection(proxy); 

你完成了。 不要忘记很好地处理exception,并且当然会更改值以适合您的场景。

啊,我省略了import语句

使用Apache commons HttpClient我也发现了以下工作(为了清楚起见,删除了try / catch):

 HostConfiguration hostConfiguration = new HostConfiguration(); byte b[] = new byte[4]; b[0] = new Integer(192).byteValue(); b[1] = new Integer(168).byteValue(); b[2] = new Integer(1).byteValue(); b[3] = new Integer(11).byteValue(); hostConfiguration.setLocalAddress(InetAddress.getByAddress(b)); HttpClient client = new HttpClient(); client.setHostConfiguration(hostConfiguration); GetMethod method = new GetMethod("http://remoteserver/"); method.getParams().setParameter(HttpMethodParams.RETRY_HANDLER, new DefaultHttpMethodRetryHandler(3, false)); int statusCode = client.executeMethod(method); if (statusCode != HttpStatus.SC_OK) { System.err.println("Method failed: " + method.getStatusLine()); } byte[] responseBody = method.getResponseBody(); System.out.println(new String(responseBody));"); 

但是,我仍然想知道如果IP的网关关闭会发生什么(在这种情况下为192.168.1.11)。 下一个网关会被尝试还是会失败?

明显的可移植方式是在URL.openConnection中设置代理。 代理可以在本地主机中,然后您可以编写一个非常简单的代理来绑定客户端套接字的本地地址。

如果无法修改URL所连接的源,则可以在调用URL构造函数时替换URLStreamHandler,也可以通过URL.setURLStreamHandlerFactory全局替换URLStreamHandler。 然后,URLStreamHandler可以委托默认的http / https处理程序,修改openConnection调用。

更极端的方法是完全替换处理程序(可能在JRE中扩展实现)。 或者,可以使用备用(开源)http客户端。

手动设置sockets工作正常…

 private HttpsURLConnection openConnection(URL src, URL dest, SSLContext sslContext) throws IOException, ProtocolException { HttpsURLConnection connection = (HttpsURLConnection) dest.openConnection(); HttpsHostNameVerifier httpsHostNameVerifier = new HttpsHostNameVerifier(); connection.setHostnameVerifier(httpsHostNameVerifier); connection.setConnectTimeout(CONNECT_TIMEOUT); connection.setReadTimeout(READ_TIMEOUT); connection.setRequestMethod(POST_METHOD); connection.setRequestProperty(CONTENT_TYPE, SoapConstants.CONTENT_TYPE_HEADER); connection.setDoOutput(true); connection.setDoInput(true); connection.setSSLSocketFactory(sslContext.getSocketFactory()); if ( src!=null ) { InetAddress inetAddress = InetAddress.getByName(src.getHost()); int destPort = dest.getPort(); if ( destPort <=0 ) destPort=SERVER_HTTPS_PORT; int srcPort = src.getPort(); if ( srcPort <=0 ) srcPort=CLIENT_HTTPS_PORT; connectionSocket = connection.getSSLSocketFactory().createSocket(dest.getHost(), destPort, inetAddress, srcPort); } connection.connect(); return connection; }