001 //$HeadURL: https://svn.wald.intevation.org/svn/deegree/base/branches/2.4_testing/src/org/deegree/framework/util/HttpUtils.java $
002 /*---------------- FILE HEADER ------------------------------------------
003 This file is part of deegree.
004 Copyright (C) 2001-2008 by:
005 Department of Geography, University of Bonn
006 http://www.giub.uni-bonn.de/deegree/
007 lat/lon GmbH
008 http://www.lat-lon.de
009
010 This library is free software; you can redistribute it and/or
011 modify it under the terms of the GNU Lesser General Public
012 License as published by the Free Software Foundation; either
013 version 2.1 of the License, or (at your option) any later version.
014 This library is distributed in the hope that it will be useful,
015 but WITHOUT ANY WARRANTY; without even the implied warranty of
016 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
017 Lesser General Public License for more details.
018 You should have received a copy of the GNU Lesser General Public
019 License along with this library; if not, write to the Free Software
020 Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
021 Contact:
022
023 Andreas Poth
024 lat/lon GmbH
025 Aennchenstr. 19
026 53177 Bonn
027 Germany
028 E-Mail: poth@lat-lon.de
029
030 Prof. Dr. Klaus Greve
031 Department of Geography
032 University of Bonn
033 Meckenheimer Allee 166
034 53115 Bonn
035 Germany
036 E-Mail: greve@giub.uni-bonn.de
037 ---------------------------------------------------------------------------*/
038
039 package org.deegree.framework.util;
040
041 import java.io.ByteArrayOutputStream;
042 import java.io.IOException;
043 import java.io.InputStream;
044 import java.net.HttpURLConnection;
045 import java.net.InetAddress;
046 import java.net.MalformedURLException;
047 import java.net.URISyntaxException;
048 import java.net.URL;
049 import java.util.Map;
050 import java.util.Properties;
051
052 import javax.xml.transform.OutputKeys;
053
054 import org.apache.commons.codec.binary.Base64;
055 import org.apache.commons.httpclient.HttpClient;
056 import org.apache.commons.httpclient.HttpException;
057 import org.apache.commons.httpclient.HttpMethod;
058 import org.apache.commons.httpclient.methods.ByteArrayRequestEntity;
059 import org.apache.commons.httpclient.methods.GetMethod;
060 import org.apache.commons.httpclient.methods.HeadMethod;
061 import org.apache.commons.httpclient.methods.InputStreamRequestEntity;
062 import org.apache.commons.httpclient.methods.PostMethod;
063 import org.apache.commons.httpclient.methods.StringRequestEntity;
064 import org.deegree.enterprise.WebUtils;
065 import org.deegree.framework.log.ILogger;
066 import org.deegree.framework.log.LoggerFactory;
067 import org.deegree.framework.xml.XMLFragment;
068
069 /**
070 * utility class for performing HTTP requests
071 *
072 * @author <a href="mailto:poth@lat-lon.de">Andreas Poth</a>
073 * @author last edited by: $Author: apoth $
074 *
075 * @version. $Revision: 25236 $, $Date: 2010-07-09 11:29:33 +0200 (Fr, 09. Jul 2010) $
076 */
077 public class HttpUtils {
078
079 private static final ILogger LOG = LoggerFactory.getLogger( HttpUtils.class );
080
081 /**
082 * validates passed URL. If it is not a valid URL or a client can not connect to it an exception will be thrown
083 *
084 * @param url
085 * @throws IOException
086 */
087 public static int validateURL( String url )
088 throws IOException {
089 return validateURL( url, null, null );
090 }
091
092 /**
093 * validates passed URL. If it is not a valid URL or a client can not connect to it an exception will be thrown
094 *
095 * @param url
096 * @param user
097 * @param password
098 * @throws IOException
099 */
100 public static int validateURL( String url, String user, String password )
101 throws IOException {
102 if ( url.startsWith( "http:" ) ) {
103 URL tmp = new URL( url );
104 HeadMethod hm = new HeadMethod( url );
105 setHTTPCredentials( hm, user, password );
106 InetAddress.getByName( tmp.getHost() );
107 HttpClient client = new HttpClient();
108 client.executeMethod( hm );
109 if ( hm.getStatusCode() != HttpURLConnection.HTTP_OK ) {
110 if ( hm.getStatusCode() != HttpURLConnection.HTTP_UNAUTHORIZED && hm.getStatusCode() != 401 ) {
111 // this method just evaluates if a URL/host is valid; it does not takes care
112 // if authorization is available/valid
113 throw new IOException( "Host " + tmp.getHost() + " of URL + " + url + " does not exists" );
114 }
115 }
116 return hm.getStatusCode();
117 } else if ( url.startsWith( "file:" ) ) {
118 URL tmp = new URL( url );
119 InputStream is = tmp.openStream();
120 is.close();
121 return 200;
122 }
123 return HttpURLConnection.HTTP_UNAVAILABLE;
124 }
125
126 /**
127 *
128 * @param url
129 * @param content
130 * @param timeout
131 * timeout in milliseconds
132 * @param user
133 * (can be <code>null</code>)
134 * @param password
135 * (can be <code>null</code>)
136 * @param contentType
137 * request content mime type (can be <code>null</code>)
138 * @param encoding
139 * request encoding (can be <code>null</code>)
140 * @param header
141 * not supported yet
142 * @return result of http post request
143 * @throws HttpException
144 * @throws IOException
145 */
146 public static HttpMethod performHttpPost( String url, InputStream content, int timeout, String user,
147 String password, String contentType, String encoding,
148 Map<String, String> header )
149 throws HttpException, IOException {
150 HttpClient client = new HttpClient();
151 URL tmp = new URL( url );
152 WebUtils.enableProxyUsage( client, tmp );
153 url = tmp.toExternalForm();
154 client.getHttpConnectionManager().getParams().setSoTimeout( timeout );
155 client.getHttpConnectionManager().getParams().setConnectionTimeout( timeout );
156
157 PostMethod pm = new PostMethod( url );
158 String ct = contentType;
159 if ( ct != null && encoding != null ) {
160 ct += ( "; " + encoding );
161 }
162 if ( ct != null ) {
163 pm.setRequestEntity( new InputStreamRequestEntity( content, ct ) );
164 } else {
165 pm.setRequestEntity( new InputStreamRequestEntity( content ) );
166 }
167
168 setHTTPCredentials( pm, user, password );
169 client.executeMethod( pm );
170 if ( LOG.getLevel() == ILogger.LOG_DEBUG ) {
171 LOG.logDebug( pm.getResponseBodyAsString() );
172 }
173 if ( pm.getStatusCode() != 200 ) {
174 throw new HttpException( "status code: " + pm.getStatusCode() );
175 }
176 return pm;
177 }
178
179 /**
180 *
181 * @param url
182 * @param content
183 * @param timeout
184 * timeout in milliseconds
185 * @param user
186 * (can <code>null</code>)
187 * @param password
188 * (can <code>null</code>)
189 * @param contentType
190 * request content mime type (can be <code>null</code>)
191 * @param encoding
192 * request encoding (can be <code>null</code>)
193 * @param header
194 * not supported yet
195 * @return result of http post request
196 * @throws HttpException
197 * @throws IOException
198 */
199 public static HttpMethod performHttpPost( String url, String content, int timeout, String user, String password,
200 String contentType, String encoding, Map<String, String> header )
201 throws HttpException, IOException {
202 HttpClient client = new HttpClient();
203 URL tmp = new URL( url );
204 WebUtils.enableProxyUsage( client, tmp );
205 url = tmp.toExternalForm();
206 client.getHttpConnectionManager().getParams().setSoTimeout( timeout );
207 client.getHttpConnectionManager().getParams().setConnectionTimeout( timeout );
208 PostMethod pm = new PostMethod( url );
209
210 pm.setRequestEntity( new StringRequestEntity( content, contentType, encoding ) );
211
212 setHTTPCredentials( pm, user, password );
213 client.executeMethod( pm );
214 if ( LOG.getLevel() == ILogger.LOG_DEBUG ) {
215 LOG.logDebug( pm.getResponseBodyAsString() );
216 }
217 if ( pm.getStatusCode() != 200 ) {
218 throw new HttpException( "status code: " + pm.getStatusCode() );
219 }
220 return pm;
221 }
222
223 /**
224 *
225 * @param url
226 * @param content
227 * @param timeout
228 * timeout in milliseconds
229 * @param user
230 * (can <code>null</code>)
231 * @param password
232 * (can <code>null</code>)
233 * @param header
234 * not supported yet
235 * @return result of http post request
236 * @throws HttpException
237 * @throws IOException
238 */
239 public static HttpMethod performHttpPost( String url, XMLFragment content, int timeout, String user, String password,
240 Map<String, String> header )
241 throws HttpException, IOException {
242 HttpClient client = new HttpClient();
243 URL tmp = new URL( url );
244 WebUtils.enableProxyUsage( client, tmp );
245 url = tmp.toExternalForm();
246 client.getHttpConnectionManager().getParams().setSoTimeout( timeout );
247 client.getHttpConnectionManager().getParams().setConnectionTimeout( timeout );
248 PostMethod pm = new PostMethod( url );
249
250 ByteArrayOutputStream bos = new ByteArrayOutputStream( 1000000 );
251 Properties props = new Properties();
252 props.put( OutputKeys.ENCODING, "UTF-8" );
253 content.write( bos, props );
254 bos.close();
255 pm.setRequestEntity( new ByteArrayRequestEntity( bos.toByteArray(), "text/xml" ) );
256
257 setHTTPCredentials( pm, user, password );
258 client.executeMethod( pm );
259 if ( LOG.getLevel() == ILogger.LOG_DEBUG ) {
260 LOG.logDebug( pm.getResponseBodyAsString() );
261 }
262 if ( pm.getStatusCode() != 200 ) {
263 throw new HttpException( "status code: " + pm.getStatusCode() );
264 }
265 return pm;
266 }
267
268 /**
269 *
270 * @param url
271 * e.g. http://localhost:8080/deegree/services
272 * @param request
273 * e.g. service=WMS&request=GetCapabilities
274 * @param timeout
275 * timeout in milliseconds
276 * @param user
277 * (can be <code>null</code>)
278 * @param password
279 * (can be <code>null</code>)
280 * @param header
281 * (not supported yet)
282 * @return result of http get request
283 * @throws HttpException
284 * @throws IOException
285 */
286 public static HttpMethod performHttpGet( String url, String request, int timeout, String user, String password,
287 Map<String, String> header )
288 throws HttpException, IOException {
289 if ( request != null && request.startsWith( "&" ) ) {
290 request = request.substring( 1 );
291 }
292 if ( url != null && url.endsWith( "?" ) ) {
293 url = url.substring( 0, url.length() - 1 );
294 }
295 LOG.logDebug( "HTTP GET URL: ", url );
296 LOG.logDebug( "HTTP GET request: ", request );
297 GetMethod gm = null;
298 if ( url.indexOf( '?' ) > -1 && request != null ) {
299 gm = new GetMethod( StringTools.concat( 500, url, '&', request ) );
300 } else if ( request != null && !request.startsWith( "http://" ) ) {
301 gm = new GetMethod( StringTools.concat( 500, url, '?', request ) );
302 } else if ( request != null && request.startsWith( "http://" ) ) {
303 gm = new GetMethod( request );
304 } else {
305 gm = new GetMethod( url );
306 }
307
308 setHTTPCredentials( gm, user, password );
309
310 HttpClient client = new HttpClient();
311 client.getHttpConnectionManager().getParams().setSoTimeout( timeout );
312 client.getHttpConnectionManager().getParams().setConnectionTimeout( timeout );
313 WebUtils.enableProxyUsage( client, new URL( url ) );
314 client.executeMethod( gm );
315 if ( LOG.getLevel() == ILogger.LOG_DEBUG ) {
316 LOG.logDebug( gm.getResponseBodyAsString() );
317 }
318 if ( gm.getStatusCode() != 200 ) {
319 throw new HttpException( "status code: " + gm.getStatusCode() );
320 }
321 return gm;
322 }
323
324 /**
325 *
326 * @param url
327 * @param user
328 * @param password
329 * @param sessionID
330 * @return URL with attached authentication information (if not null)
331 */
332 public static String addAuthenticationForKVP( String url, String user, String password, String sessionID ) {
333 if ( sessionID != null && sessionID.trim().length() > 0 ) {
334 url = url + "&sessionID=" + sessionID;
335 } else if ( user != null ) {
336 url = url + "&user=" + user;
337 if ( password == null ) {
338 password = "";
339 }
340 url = url + "&password=" + password;
341 }
342 return url;
343 }
344
345 /**
346 *
347 * @param xml
348 * @param user
349 * @param password
350 * @param sessionID
351 * @return XML document with authentication information (if not null) as attributes of the root element
352 */
353 public static XMLFragment addAuthenticationForXML( XMLFragment xml, String user, String password, String sessionID ) {
354 if ( sessionID != null ) {
355 xml.getRootElement().setAttribute( "sessionID", sessionID );
356 } else if ( user != null ) {
357 xml.getRootElement().setAttribute( "user", user );
358 if ( password != null ) {
359 xml.getRootElement().setAttribute( "password", password );
360 }
361 }
362 return xml;
363 }
364
365 /**
366 *
367 * @param url
368 * @return URL as String with protocol and path but without request params
369 * @throws URISyntaxException
370 */
371 public static String normalizeURL( URL url ) {
372 String pr = url.getProtocol();
373 String ho = url.getHost();
374 int po = url.getPort();
375 String pa = url.getPath();
376 String s = pr + "://" + ho + ':' + po;
377 if ( pa != null && pa.length() > 0 ) {
378 s += pa;
379 }
380 return s;
381 }
382
383 /**
384 *
385 * @param url
386 * @return URL as String with protocol and path but without request params
387 * @throws URISyntaxException
388 */
389 public static String normalizeURL( String url ) {
390 try {
391 return normalizeURL( new URL( url ) );
392 } catch ( MalformedURLException e ) {
393 LOG.logWarning( e.getMessage(), e );
394 }
395 return url;
396 }
397
398 private static void setHTTPCredentials( HttpMethod m, String user, String password ) {
399 if ( user != null ) {
400 if ( password == null ) {
401 password = "";
402 }
403 String s = new String( Base64.encodeBase64( ( user + ":" + password ).getBytes() ) );
404 m.setRequestHeader( "authorization", "Basic " + s );
405 }
406 }
407
408 }