1. /*
  2. * Copyright 2000-2004 The Apache Software Foundation
  3. *
  4. * Licensed under the Apache License, Version 2.0 (the "License");
  5. * you may not use this file except in compliance with the License.
  6. * You may obtain a copy of the License at
  7. *
  8. * http://www.apache.org/licenses/LICENSE-2.0
  9. *
  10. * Unless required by applicable law or agreed to in writing, software
  11. * distributed under the License is distributed on an "AS IS" BASIS,
  12. * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  13. * See the License for the specific language governing permissions and
  14. * limitations under the License.
  15. *
  16. */
  17. package org.apache.tools.ant.taskdefs.optional.net;
  18. import java.lang.reflect.InvocationTargetException;
  19. import java.lang.reflect.Method;
  20. import java.util.Properties;
  21. import org.apache.tools.ant.BuildException;
  22. import org.apache.tools.ant.Project;
  23. import org.apache.tools.ant.Task;
  24. import org.apache.tools.ant.util.JavaEnvUtils;
  25. /**
  26. * Sets Java's web proxy properties, so that tasks and code run in
  27. * the same JVM can have through-the-firewall access to remote web sites,
  28. * and remote ftp sites.
  29. * You can nominate an http and ftp proxy, or a socks server, reset the server
  30. * settings, or do nothing at all.
  31. * <p>
  32. * Examples
  33. * <pre><setproxy/></pre>
  34. * do nothing
  35. * <pre><setproxy proxyhost="firewall"/></pre>
  36. * set the proxy to firewall:80
  37. * <pre><setproxy proxyhost="firewall" proxyport="81"/></pre>
  38. * set the proxy to firewall:81
  39. * <pre><setproxy proxyhost=""/></pre>
  40. * stop using the http proxy; don't change the socks settings
  41. * <pre><setproxy socksproxyhost="socksy"/></pre>
  42. * use socks via socksy:1080
  43. * <pre><setproxy socksproxyhost=""/></pre>
  44. * stop using the socks server.
  45. * <p>
  46. * You can set a username and password for http with the <tt>proxyHost</tt>
  47. * and <tt>proxyPassword</tt> attributes. On Java1.4 and above these can also be
  48. * used against SOCKS5 servers.
  49. * </p>
  50. * @see <a href="http://java.sun.com/j2se/1.4/docs/guide/net/properties.html">
  51. * java 1.4 network property list</a>
  52. *@since Ant 1.5
  53. * @ant.task category="network"
  54. */
  55. public class SetProxy extends Task {
  56. /**
  57. * proxy details
  58. */
  59. protected String proxyHost = null;
  60. /**
  61. * name of proxy port
  62. */
  63. protected int proxyPort = 80;
  64. /**
  65. * socks host.
  66. */
  67. private String socksProxyHost = null;
  68. /**
  69. * Socks proxy port. Default is 1080.
  70. */
  71. private int socksProxyPort = 1080;
  72. /**
  73. * list of non proxy hosts
  74. */
  75. private String nonProxyHosts = null;
  76. /**
  77. * user for http only
  78. */
  79. private String proxyUser = null;
  80. /**
  81. * password for http only
  82. */
  83. private String proxyPassword = null;
  84. /**
  85. * the HTTP/ftp proxy host. Set this to "" for the http proxy
  86. * option to be disabled
  87. *
  88. * @param hostname the new proxy hostname
  89. */
  90. public void setProxyHost(String hostname) {
  91. proxyHost = hostname;
  92. }
  93. /**
  94. * the HTTP/ftp proxy port number; default is 80
  95. *
  96. * @param port port number of the proxy
  97. */
  98. public void setProxyPort(int port) {
  99. proxyPort = port;
  100. }
  101. /**
  102. * The name of a Socks server. Set to "" to turn socks
  103. * proxying off.
  104. *
  105. * @param host The new SocksProxyHost value
  106. */
  107. public void setSocksProxyHost(String host) {
  108. this.socksProxyHost = host;
  109. }
  110. /**
  111. * Set the ProxyPort for socks connections. The default value is 1080
  112. *
  113. * @param port The new SocksProxyPort value
  114. */
  115. public void setSocksProxyPort(int port) {
  116. this.socksProxyPort = port;
  117. }
  118. /**
  119. * A list of hosts to bypass the proxy on. These should be separated
  120. * with the vertical bar character '|'. Only in Java 1.4 does ftp use
  121. * this list.
  122. * e.g. fozbot.corp.sun.com|*.eng.sun.com
  123. * @param nonProxyHosts lists of hosts to talk direct to
  124. */
  125. public void setNonProxyHosts(String nonProxyHosts) {
  126. this.nonProxyHosts = nonProxyHosts;
  127. }
  128. /**
  129. * set the proxy user. Probably requires a password to accompany this
  130. * setting. Default=""
  131. * @param proxyUser username
  132. * @since Ant1.6
  133. */
  134. public void setProxyUser(String proxyUser) {
  135. this.proxyUser = proxyUser;
  136. }
  137. /**
  138. * Set the password for the proxy. Used only if the proxyUser is set.
  139. * @param proxyPassword password to go with the username
  140. * @since Ant1.6
  141. */
  142. public void setProxyPassword(String proxyPassword) {
  143. this.proxyPassword = proxyPassword;
  144. }
  145. /**
  146. * if the proxy port and host settings are not null, then the settings
  147. * get applied these settings last beyond the life of the object and
  148. * apply to all network connections
  149. * Relevant docs: buglist #4183340
  150. */
  151. public void applyWebProxySettings() {
  152. boolean settingsChanged = false;
  153. boolean enablingProxy = false;
  154. Properties sysprops = System.getProperties();
  155. if (proxyHost != null) {
  156. settingsChanged = true;
  157. if (proxyHost.length() != 0) {
  158. traceSettingInfo();
  159. enablingProxy = true;
  160. sysprops.put("http.proxyHost", proxyHost);
  161. String portString = Integer.toString(proxyPort);
  162. sysprops.put("http.proxyPort", portString);
  163. sysprops.put("https.proxyHost", proxyHost);
  164. sysprops.put("https.proxyPort", portString);
  165. sysprops.put("ftp.proxyHost", proxyHost);
  166. sysprops.put("ftp.proxyPort", portString);
  167. if (nonProxyHosts != null) {
  168. sysprops.put("http.nonProxyHosts", nonProxyHosts);
  169. sysprops.put("https.nonProxyHosts", nonProxyHosts);
  170. sysprops.put("ftp.nonProxyHosts", nonProxyHosts);
  171. }
  172. if (proxyUser != null) {
  173. sysprops.put("http.proxyUser", proxyUser);
  174. sysprops.put("http.proxyPassword", proxyPassword);
  175. }
  176. } else {
  177. log("resetting http proxy", Project.MSG_VERBOSE);
  178. sysprops.remove("http.proxyHost");
  179. sysprops.remove("http.proxyPort");
  180. sysprops.remove("http.proxyUser");
  181. sysprops.remove("http.proxyPassword");
  182. sysprops.remove("https.proxyHost");
  183. sysprops.remove("https.proxyPort");
  184. sysprops.remove("ftp.proxyHost");
  185. sysprops.remove("ftp.proxyPort");
  186. }
  187. }
  188. //socks
  189. if (socksProxyHost != null) {
  190. settingsChanged = true;
  191. if (socksProxyHost.length() != 0) {
  192. enablingProxy = true;
  193. sysprops.put("socksProxyHost", socksProxyHost);
  194. sysprops.put("socksProxyPort", Integer.toString(socksProxyPort));
  195. if (proxyUser != null) {
  196. //this may be a java1.4 thingy only
  197. sysprops.put("java.net.socks.username", proxyUser);
  198. sysprops.put("java.net.socks.password", proxyPassword);
  199. }
  200. } else {
  201. log("resetting socks proxy", Project.MSG_VERBOSE);
  202. sysprops.remove("socksProxyHost");
  203. sysprops.remove("socksProxyPort");
  204. sysprops.remove("java.net.socks.username");
  205. sysprops.remove("java.net.socks.password");
  206. }
  207. }
  208. //for Java1.1 we need to tell the system that the settings are new
  209. if (settingsChanged
  210. && JavaEnvUtils.isJavaVersion(JavaEnvUtils.JAVA_1_1)) {
  211. legacyResetProxySettingsCall(enablingProxy);
  212. }
  213. }
  214. /**
  215. * list out what is going on
  216. */
  217. private void traceSettingInfo() {
  218. log("Setting proxy to "
  219. + (proxyHost != null ? proxyHost : "''")
  220. + ":" + proxyPort,
  221. Project.MSG_VERBOSE);
  222. }
  223. /**
  224. * make a call to sun.net.www.http.HttpClient.resetProperties();
  225. * this is only needed for java 1.1; reflection is used to stop the compiler
  226. * whining, and in case cleanroom JVMs dont have the class.
  227. * @return true if we did something
  228. */
  229. protected boolean legacyResetProxySettingsCall(boolean setProxy) {
  230. System.getProperties().put("http.proxySet", new Boolean(setProxy).toString());
  231. try {
  232. Class c = Class.forName("sun.net.www.http.HttpClient");
  233. Method reset = c.getMethod("resetProperties", null);
  234. reset.invoke(null, null);
  235. return true;
  236. } catch (ClassNotFoundException cnfe) {
  237. return false;
  238. } catch (NoSuchMethodException e) {
  239. return false;
  240. } catch (IllegalAccessException e) {
  241. return false;
  242. } catch (InvocationTargetException e) {
  243. return false;
  244. }
  245. }
  246. /**
  247. * Does the work.
  248. *
  249. * @exception BuildException thrown in unrecoverable error.
  250. */
  251. public void execute() throws BuildException {
  252. applyWebProxySettings();
  253. }
  254. }