Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/java/395.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java 使用Socks 4代理的HTTP调用_Java_Proxy_Socks - Fatal编程技术网

Java 使用Socks 4代理的HTTP调用

Java 使用Socks 4代理的HTTP调用,java,proxy,socks,Java,Proxy,Socks,我需要使用socks 4代理调用服务器。我使用的是java版本1.6 如果我们使用类似的东西,那么它将SOCKS代理视为版本5 URL url = new URL("https://www.google.com"); URLConnection connection = null; SocketAddress proxySocketAddress1 = new InetSocketAddress("XXXXXXXXXX", 8081); Proxy proxy = new

我需要使用socks 4代理调用服务器。我使用的是java版本1.6

如果我们使用类似的东西,那么它将SOCKS代理视为版本5

 URL url = new URL("https://www.google.com");  
 URLConnection connection = null;  
 SocketAddress proxySocketAddress1 =  new InetSocketAddress("XXXXXXXXXX", 8081);  
 Proxy proxy = new Proxy(Proxy.Type.SOCKS, proxySocketAddress1);  
 connection = url.openConnection(proxy);  
 connection.setConnectTimeout(150000);  
 connection.connect();  
我可以通过执行以下操作在系统级别设置socks代理

// Set SOCKS proxy
System.getProperties().put( "socksProxyHost","xxxxx");
System.getProperties().put( "socksProxyPort","1234");
System.getProperties().put("socksProxyVersion","4");
当我这样做时,我能够到达服务器

connection = url.openConnection(); 
但我的其他连接,比如到db的连接,加密服务器也会通过代理并失败

我还尝试从系统代理中排除服务器,但没有成功

System.getProperties().put("socksnonProxyHosts","*.net");
System.getProperties().put("http.nonProxyHosts","*.net"); 

在java 1.6中有没有其他方法可以选择使用SOCKS4。

这是
socksocketimpl
实现中的一个错误:


这是我尝试过的,看起来很有效。基本上,我需要SOCKS4代理来连接到套接字

SocketAddress socketAddress =  new InetSocketAddress("proxyhost",proxyport);
Proxy socketProxy =  new Proxy(Proxy.Type.SOCKS, socketAddress);

Socket  socket = new Socket(socketProxy); 
Class clazzSocks  = socket.getClass();
Method setSockVersion  = null;
Field sockImplField = null; 
SocketImpl socksimpl = null; 
 try {
    sockImplField = clazzSocks.getDeclaredField("impl");
    sockImplField.setAccessible(true);
    socksimpl  = (SocketImpl) sockImplField.get(socket);
    Class clazzSocksImpl  =  socksimpl.getClass();
    setSockVersion  = clazzSocksImpl.getDeclaredMethod("setV4");
    setSockVersion.setAccessible(true);
    if(null != setSockVersion){
        setSockVersion.invoke(socksimpl);
    }
    sockImplField.set(socket, socksimpl);
    } 
        catch (Exception e) {
      // TODO Auto-generated catch block
            e.printStackTrace();
    } 

String hostName="xxxxx";
int port=1080;
InetAddress address;        
SocketAddress socketAddress;            
address = InetAddress.getByName(hostName);
socketAddress = new InetSocketAddress(address, port);

// Connect to socket
socket.connect(socketAddress, 100000);

//setting the socket read() connection time out 
socket.setSoTimeout(100000);    

请分享您对该方法的意见和反馈

注意,它在Java7中被列为固定的。有没有任何方法可以使用标准jdk库在任何jdk中使用SOCKS4代理?我读过这个bug,它说:“提议的socksProxyVersion属性对通过java.net.Proxy编程设置的SOCKS代理没有任何影响”。这意味着我不能在单个套接字连接上设置它。您是否考虑过编写自己的
代理
派生类来自己实现SOCKS v4?这是一个手动实现的非常简单的协议。
socksnonProxyHosts
中没有列出,也没有类似的内容。(也不是
socksProxyVersion,
,但是@RemyLebeau给出的bug链接将其描述为在Java 7中添加的。)因为SocksSocketImpl类不是公共的,所以我使用反射来访问setV4方法。从技术上看,它似乎是正确的,也能正常工作。只是想得到一些合理的反馈。