实际上,只需使用增强的 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);