ProxySelector:每个代理不同 URL
ProxySelector: Different Proxy for Each URL
我正在尝试了解 ProxySelector class 的工作原理。我当前的代码如下所示:
URI uri = new URI("http://google.com");
proxySelector.select(uri);
我知道在调用 proxySelector.select(uri);
时,这是假设 return 相应 URI 的代理列表。但我看不到如何为每个 URI 设置代理。
我知道我可以使用 setDefault()
方法设置默认代理,但据我所知,这将设置系统范围的代理,而不是特定 URI
.[=16 的代理=]
我可能在这里遗漏了一些基本点,但是如何为 url A(例如 http://google.com) and a different proxy for url B (such as http://ebay.com)设置一个代理,然后让系统自动 select 正确的代理每次连接到对应的 url?
重写 ProxySelector.select(URI uri)
方法,您可以在其中实现自定义逻辑来为 URI 选择正确的代理或代理列表。
通过调用 ProxySelector.setDefault(customProxySelector)
.
将新的自定义 ProxySelector
设置为系统范围
URLConnection
的任何子类都将使用 ProxySelector
,例如:
URLConnection conn = url.openConnection();
或配置您将用于调用远程 URI 的框架,例如 Spring RestTemplate:
HttpRoutePlanner routePlanner = new SystemDefaultRoutePlanner(new MyProxySelector());
HttpComponentsClientHttpRequestFactory clientHttpRequestFactory
= new HttpComponentsClientHttpRequestFactory(
HttpClientBuilder.create()
.setRoutePlanner(routePlanner)
.build());
restTemplate = new RestTemplate(clientHttpRequestFactory);
最好回退到自定义 select(URI uri)
中的默认 ProxySelector,以防自定义逻辑无法为 uri 确定合适的代理。
请参阅我对 的其他回答。
网络和代理在 Java Networking and Proxies (paragraph 4 ProxySelector) and ProxySelector Java docs 中有很好的解释。
实际上,通过使用增强的 ProxySelector,它在没有任何反射的情况下工作得很好,它支持特定 url 的白名单并将其余部分传递给委托(也称为默认)ProxySelector。
public class DelegatingProxySelector extends ProxySelector {
private final Set<URI> allProxiedUri = new HashSet<>();
private String proxyHost;
private Integer proxyPort;
private final ProxySelector delegate;
public DelegatingProxySelector(
String proxyHost, Integer proxyPort, ProxySelector delegate) {
this.proxyHost = proxyHost;
this.proxyPort = proxyPort;
this.delegate = delegate;
}
@Override
public List<Proxy> select(final URI uri) {
if (allProxiedUri.contains(uri)) {
final InetSocketAddress proxyAddress = InetSocketAddress
.createUnresolved(proxyHost, proxyPort);
return Collections.singletonList(new Proxy(Type.HTTP, proxyAddress));
}
return delegate.select(uri);
}
@Override
public void connectFailed(final URI uri, final SocketAddress sa, final IOException ioe) {
System.err.println("Unable to reach uri " + uri + " via proxy: " + ioe.getMessage());
}
public void addProxiedUri(URI uri) {
allProxiedUri.add(uri);
}
}
...
final DelegatingProxySelector delegatingProxySelector = new DelegatingProxySelector("localhost", 3128, ProxySelector.getDefault());
ProxySelector.setDefault(delegatingProxySelector);
我正在尝试了解 ProxySelector class 的工作原理。我当前的代码如下所示:
URI uri = new URI("http://google.com");
proxySelector.select(uri);
我知道在调用 proxySelector.select(uri);
时,这是假设 return 相应 URI 的代理列表。但我看不到如何为每个 URI 设置代理。
我知道我可以使用 setDefault()
方法设置默认代理,但据我所知,这将设置系统范围的代理,而不是特定 URI
.[=16 的代理=]
我可能在这里遗漏了一些基本点,但是如何为 url A(例如 http://google.com) and a different proxy for url B (such as http://ebay.com)设置一个代理,然后让系统自动 select 正确的代理每次连接到对应的 url?
重写
ProxySelector.select(URI uri)
方法,您可以在其中实现自定义逻辑来为 URI 选择正确的代理或代理列表。通过调用
将新的自定义ProxySelector.setDefault(customProxySelector)
.ProxySelector
设置为系统范围URLConnection
的任何子类都将使用ProxySelector
,例如:URLConnection conn = url.openConnection();
或配置您将用于调用远程 URI 的框架,例如 Spring RestTemplate:
HttpRoutePlanner routePlanner = new SystemDefaultRoutePlanner(new MyProxySelector()); HttpComponentsClientHttpRequestFactory clientHttpRequestFactory = new HttpComponentsClientHttpRequestFactory( HttpClientBuilder.create() .setRoutePlanner(routePlanner) .build()); restTemplate = new RestTemplate(clientHttpRequestFactory);
最好回退到自定义 select(URI uri)
中的默认 ProxySelector,以防自定义逻辑无法为 uri 确定合适的代理。
请参阅我对
网络和代理在 Java Networking and Proxies (paragraph 4 ProxySelector) and ProxySelector Java docs 中有很好的解释。
实际上,通过使用增强的 ProxySelector,它在没有任何反射的情况下工作得很好,它支持特定 url 的白名单并将其余部分传递给委托(也称为默认)ProxySelector。
public class DelegatingProxySelector extends ProxySelector {
private final Set<URI> allProxiedUri = new HashSet<>();
private String proxyHost;
private Integer proxyPort;
private final ProxySelector delegate;
public DelegatingProxySelector(
String proxyHost, Integer proxyPort, ProxySelector delegate) {
this.proxyHost = proxyHost;
this.proxyPort = proxyPort;
this.delegate = delegate;
}
@Override
public List<Proxy> select(final URI uri) {
if (allProxiedUri.contains(uri)) {
final InetSocketAddress proxyAddress = InetSocketAddress
.createUnresolved(proxyHost, proxyPort);
return Collections.singletonList(new Proxy(Type.HTTP, proxyAddress));
}
return delegate.select(uri);
}
@Override
public void connectFailed(final URI uri, final SocketAddress sa, final IOException ioe) {
System.err.println("Unable to reach uri " + uri + " via proxy: " + ioe.getMessage());
}
public void addProxiedUri(URI uri) {
allProxiedUri.add(uri);
}
}
...
final DelegatingProxySelector delegatingProxySelector = new DelegatingProxySelector("localhost", 3128, ProxySelector.getDefault());
ProxySelector.setDefault(delegatingProxySelector);