很多时候,Java应用程序需要连接到Internet。最常见的例子发生在读取XML文件并需要下载其模式时。

我在代理服务器后面。如何将JVM设置为使用代理?


当前回答

正如在其他回答中指出的那样,如果您需要使用经过身份验证的代理,纯粹使用命令行变量是没有可靠的方法来做到这一点的——如果您正在使用别人的应用程序,并且不想弄乱源代码,这是很烦人的。

Will Iverson在使用HttpProxy连接到具有抢先身份验证的主机上提出了有用的建议,使用代理管理工具如proxfier (http://www.proxifier.com/ for Mac OS X和Windows)来处理这个问题。

例如,使用proxfier,您可以将其设置为仅拦截要通过其(经过身份验证的)代理进行管理和重定向的java命令。在这种情况下,你需要将proxyHost和proxyPort的值设置为空,例如传入-Dhttp。proxyHost = -Dhttp。proxyPort=到您的java命令。

其他回答

你可以通过编程的方式设置这些标志:

if (needsProxy()) {
    System.setProperty("http.proxyHost",getProxyHost());
    System.setProperty("http.proxyPort",getProxyPort());
} else {
    System.setProperty("http.proxyHost","");
    System.setProperty("http.proxyPort","");
}

只要从方法needsProxy(), getProxyHost()和getProxyPort()中返回正确的值,您就可以随时调用此代码片段。

下面展示了如何在Java中通过命令行设置具有代理用户和代理密码的代理,这是一种非常常见的情况。首先,您不应该在代码中保存密码和主机,这是一个规则。

在命令行中使用-D传递系统属性,并使用system在代码中设置它们。setProperty("name", "value")是等价的。

但是请注意

工作的例子:

C:\temp>java -Dhttps.proxyHost=host -Dhttps.proxyPort=port -Dhttps.proxyUser=user -Dhttps.proxyPassword="password" -Djavax.net.ssl.trustStore=c:/cacerts -Djavax.net.ssl.trustStorePassword=changeit com.andreas.JavaNetHttpConnection

但是下面的方法不起作用:

C:\temp>java com.andreas.JavaNetHttpConnection -Dhttps.proxyHost=host -Dhttps.proxyPort=port -Dhttps=proxyUser=user -Dhttps.proxyPassword="password" -Djavax.net.ssl.trustStore=c:/cacerts -Djavax.net.ssl.trustStorePassword=changeit

唯一的区别是系统属性的位置!(上课前后)

如果你的密码中有特殊字符,你可以把它放在引号中“@MyPass123%”,就像上面的例子一样。

访问HTTPS服务时,必须使用HTTPS协议。proxyHost, https。proxyPort等等。

如果访问HTTP服务,必须使用HTTP。proxyHost, http。proxyPort等等。

正如在其他回答中指出的那样,如果您需要使用经过身份验证的代理,纯粹使用命令行变量是没有可靠的方法来做到这一点的——如果您正在使用别人的应用程序,并且不想弄乱源代码,这是很烦人的。

Will Iverson在使用HttpProxy连接到具有抢先身份验证的主机上提出了有用的建议,使用代理管理工具如proxfier (http://www.proxifier.com/ for Mac OS X和Windows)来处理这个问题。

例如,使用proxfier,您可以将其设置为仅拦截要通过其(经过身份验证的)代理进行管理和重定向的java命令。在这种情况下,你需要将proxyHost和proxyPort的值设置为空,例如传入-Dhttp。proxyHost = -Dhttp。proxyPort=到您的java命令。

使用系统代理设置:

java -Djava.net.useSystemProxies=true ...

或编程:

System.setProperty("java.net.useSystemProxies", "true");

来源:http://docs.oracle.com/javase/7/docs/api/java/net/doc-files/net-properties.html

这是一个对我有用的完整示例-注意,对于HTTPS有单独的属性(根据https://docs.oracle.com/javase/8/docs/technotes/guides/net/proxies.html)。

下面的代码向https://api.myip.com API发送请求并打印响应。

public static void main(String[] args) throws IOException {
    System.setProperty("java.net.useSystemProxies", "true");
    final String proxyUser = "proxy-user";
    final String proxyPass = "password123";
    final String host = "some.proxy.io";
    final Integer port = 50201;

    // http
    System.setProperty("http.proxyHost",host);
    System.setProperty("http.proxyPort", String.valueOf(port));
    System.setProperty("http.proxyUser", proxyUser);
    System.setProperty("http.proxyPassword", proxyPass);

    // https
    System.setProperty("https.proxyHost",host);
    System.setProperty("https.proxyPort", String.valueOf(port));
    System.setProperty("https.proxyUser", proxyUser);
    System.setProperty("https.proxyPassword", proxyPass);

    System.setProperty("jdk.http.auth.tunneling.disabledSchemes", "");
    System.setProperty("jdk.https.auth.tunneling.disabledSchemes", "");

    Authenticator.setDefault(new Authenticator() {
                @Override
                public PasswordAuthentication getPasswordAuthentication() {
                    return new PasswordAuthentication(proxyUser, proxyPass.toCharArray());
                }
        }
    );

    // create and send a https request to myip.com API
    URL url = new URL("https://api.myip.com");
    HttpURLConnection connection = (HttpURLConnection) url.openConnection();
    connection.setRequestMethod("GET");
    int status = connection.getResponseCode();
    
    // read the response
    BufferedReader in = new BufferedReader(new InputStreamReader(connection.getInputStream()));
    String responseLine;
    StringBuffer responseContent = new StringBuffer();
    while ((responseLine = in.readLine()) != null) 
        responseContent.append(responseLine);
    
    in.close();
    connection.disconnect();
    
    // print the response
    System.out.println(status);
    System.out.println(responseContent);
}