From do-not-reply at jboss.org Tue Jun 29 06:35:54 2010 Content-Type: multipart/mixed; boundary="===============3672290304436851655==" MIME-Version: 1.0 From: do-not-reply at jboss.org To: exo-jcr-commits at lists.jboss.org Subject: [exo-jcr-commits] exo-jcr SVN: r2711 - in ws/trunk: exo.ws.rest.ext/src/main/java/org/exoplatform/services/rest/ext/proxy and 1 other directory. Date: Tue, 29 Jun 2010 06:35:54 -0400 Message-ID: <201006291035.o5TAZsgN032191@svn01.web.mwc.hst.phx2.redhat.com> --===============3672290304436851655== Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable Author: aparfonov Date: 2010-06-29 06:35:54 -0400 (Tue, 29 Jun 2010) New Revision: 2711 Modified: ws/trunk/exo.ws.commons/src/main/java/org/exoplatform/common/http/client= /AuthorizationInfo.java ws/trunk/exo.ws.rest.ext/src/main/java/org/exoplatform/services/rest/ext= /proxy/ProxyService.java Log: EXOJCR-800 Modified: ws/trunk/exo.ws.commons/src/main/java/org/exoplatform/common/http= /client/AuthorizationInfo.java =3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D= =3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D= =3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D --- ws/trunk/exo.ws.commons/src/main/java/org/exoplatform/common/http/clien= t/AuthorizationInfo.java 2010-06-25 14:51:32 UTC (rev 2710) +++ ws/trunk/exo.ws.commons/src/main/java/org/exoplatform/common/http/clien= t/AuthorizationInfo.java 2010-06-29 10:35:54 UTC (rev 2711) @@ -26,7 +26,7 @@ * * The HTTPClient's home page is located at: * - * http://www.innovation.ch/java/HTTPClient/ = + * http://www.innovation.ch/java/HTTPClient/ * */ = @@ -54,18 +54,18 @@ * used by the "Basic" scheme and derivatives, and the one used by the "Di= gest" * scheme and derivatives. The first form contains just the the scheme and= a * "cookie": - * = + * *
  *     Authorization: Basic aGVsbG86d29ybGQ=3D
  * 
- * = + * * The second form contains the scheme followed by a number of parameters = in the * form of name=3Dvalue pairs: - * = + * *
  *     Authorization: Digest username=3D"hello", realm=3D"t=
est", nonce=3D"42", ...
  * 
- * = + * * The two fields "cookie" and "params" correspond to these two forms. toString() is used by the AuthorizationModule = when * generating the Authorization header and will format the info accordingl= y. @@ -85,6 +85,7 @@ * methods manipulate and query an internal list of AuthorizationInfo inst= ances. * There can be only one instance per host, port, scheme, and realm combin= ation * (see equals()). + * * @version 0.3-3 06/05/2001 * @author Ronald Tschal=EF=BF=BDr * @since V0.1 @@ -113,8 +114,8 @@ private int port; = /** - * the scheme. (e.g. "Basic") Note: don't lowercase because some buggy = servers - * use a case-sensitive match + * the scheme. (e.g. "Basic") Note: don't lowercase because some buggy + * servers use a case-sensitive match */ private String scheme; = @@ -140,6 +141,7 @@ = /** * Creates an new info structure for the specified host and port. + * * @param host the host * @param port the port */ @@ -152,6 +154,7 @@ /** * Creates a new info structure for the specified host and port with the * specified scheme, realm, params. The cookie is set to null. + * * @param host the host * @param port the port * @param scheme the scheme @@ -177,13 +180,14 @@ * Creates a new info structure for the specified host and port with the * specified scheme, realm and cookie. The params is set to a zero-leng= th * array, and the extra_info is set to null. + * * @param host the host * @param port the port * @param scheme the scheme * @param realm the realm * @param cookie for the "Basic" scheme this is the base64-encoded - * username/password; for the "NTLM" scheme this is the - * base64-encoded username/password message. + * username/password; for the "NTLM" scheme this is the base64-e= ncoded + * username/password message. */ public AuthorizationInfo(String host, int port, String scheme, String r= ealm, String cookie) { @@ -199,6 +203,7 @@ = /** * Creates a new copy of the given AuthorizationInfo. + * * @param templ the info to copy */ AuthorizationInfo(AuthorizationInfo templ) @@ -217,10 +222,10 @@ // Class Methods = /** - * Set's the authorization handler. This handler is called whenever the= server - * requests authorization and no entry for the requested scheme and rea= lm can - * be found in the list. The handler must implement the AuthorizationHa= ndler - * interface. + * Set's the authorization handler. This handler is called whenever the + * server requests authorization and no entry for the requested scheme = and + * realm can be found in the list. The handler must implement the + * AuthorizationHandler interface. *

* If no handler is set then a {@link DefaultAuthHandler default handle= r} is * used. This handler currently only handles the "Basic" and "Digest" s= chemes @@ -228,6 +233,7 @@ *

* The default handler can be disabled by setting the auth handler to * null. + * * @param handler the new authorization handler * @return the old authorization handler * @see AuthorizationHandler @@ -242,6 +248,7 @@ = /** * Get's the current authorization handler. + * * @return the current authorization handler, or null if none is set. * @see AuthorizationHandler */ @@ -253,6 +260,7 @@ /** * Searches for the authorization info using the given host, port, sche= me and * realm. The context is the default context. + * * @param host the host * @param port the port * @param scheme the scheme @@ -267,6 +275,7 @@ /** * Searches for the authorization info in the given context using the g= iven * host, port, scheme and realm. + * * @param host the host * @param port the port * @param scheme the scheme @@ -287,13 +296,15 @@ /** * Queries the AuthHandler for authorization info. It also adds this in= fo to * the list. - * @param auth_info any info needed by the AuthHandler; at a minimum th= e host, - * scheme and realm should be set. + * + * @param auth_info any info needed by the AuthHandler; at a minimum the + * host, scheme and realm should be set. * @param req the request which initiated this query * @param resp the full response * @return a structure containing the requested info, or null if either= no * AuthHandler is set or the user canceled the request. - * @exception AuthSchemeNotImplException if this is thrown by the AuthH= andler. + * @exception AuthSchemeNotImplException if this is thrown by the + * AuthHandler. */ static AuthorizationInfo queryAuthHandler(AuthorizationInfo auth_info, = RoRequest req, RoResponse resp) throws AuthSchemeNotImplException, IOException @@ -317,6 +328,7 @@ * Searches for the authorization info using the host, port, scheme and= realm * from the given info struct. If not found it queries the AuthHandler = (if * set). + * * @param auth_info the AuthorizationInfo * @param req the request which initiated this query * @param resp the full response @@ -335,6 +347,11 @@ = AuthorizationInfo new_info =3D (AuthorizationInfo)AuthList.get(auth_= info); = + if (new_info =3D=3D null) + new_info =3D + (AuthorizationInfo)AuthList.get(new AuthorizationInfo(auth_inf= o.getHost(), auth_info.getPort(), auth_info + .getScheme(), null, auth_info.getParams(), auth_info.getExt= raInfo())); + if (new_info =3D=3D null && query_auth_h) new_info =3D queryAuthHandler(auth_info, req, resp); = @@ -344,6 +361,7 @@ /** * Searches for the authorization info given a host, port, scheme and r= ealm. * Queries the AuthHandler if not found in list. + * * @param host the host * @param port the port * @param scheme the scheme @@ -363,8 +381,9 @@ = /** * Adds an authorization entry to the list using the default context. I= f an - * entry for the specified scheme and realm already exists then its coo= kie and - * params are replaced with the new data. + * entry for the specified scheme and realm already exists then its coo= kie + * and params are replaced with the new data. + * * @param auth_info the AuthorizationInfo to add */ public static void addAuthorization(AuthorizationInfo auth_info) @@ -376,6 +395,7 @@ * Adds an authorization entry to the list. If an entry for the specifi= ed * scheme and realm already exists then its cookie and params are repla= ced * with the new data. + * * @param auth_info the AuthorizationInfo to add * @param context the context to associate this info with */ @@ -403,8 +423,9 @@ = /** * Adds an authorization entry to the list using the default context. I= f an - * entry for the specified scheme and realm already exists then its coo= kie and - * params are replaced with the new data. + * entry for the specified scheme and realm already exists then its coo= kie + * and params are replaced with the new data. + * * @param host the host * @param port the port * @param scheme the scheme @@ -423,6 +444,7 @@ * Adds an authorization entry to the list. If an entry for the specifi= ed * scheme and realm already exists then its cookie and params are repla= ced * with the new data. + * * @param host the host * @param port the port * @param scheme the scheme @@ -447,6 +469,7 @@ * Adds an authorization entry for the "Basic" authorization scheme to = the * list using the default context. If an entry already exists for the "= Basic" * scheme and the specified realm then it is overwritten. + * * @param host the host * @param port the port * @param realm the realm @@ -462,6 +485,7 @@ * Adds an authorization entry for the "Basic" authorization scheme to = the * list. If an entry already exists for the "Basic" scheme and the spec= ified * realm then it is overwritten. + * * @param host the host * @param port the port * @param realm the realm @@ -478,8 +502,9 @@ = /** * Adds an authorization entry for the "Digest" authorization scheme to= the - * list using the default context. If an entry already exists for the "= Digest" - * scheme and the specified realm then it is overwritten. + * list using the default context. If an entry already exists for the + * "Digest" scheme and the specified realm then it is overwritten. + * * @param host the host * @param port the port * @param realm the realm @@ -495,6 +520,7 @@ * Adds an authorization entry for the "Digest" authorization scheme to= the * list. If an entry already exists for the "Digest" scheme and the spe= cified * realm then it is overwritten. + * * @param host the host * @param port the port * @param realm the realm @@ -538,6 +564,7 @@ * Removes an authorization entry from the list using the default conte= xt. If * no entry for the specified host, port, scheme and realm exists then = this * does nothing. + * * @param auth_info the AuthorizationInfo to remove */ public static void removeAuthorization(AuthorizationInfo auth_info) @@ -546,8 +573,9 @@ } = /** - * Removes an authorization entry from the list. If no entry for the sp= ecified - * host, port, scheme and realm exists then this does nothing. + * Removes an authorization entry from the list. If no entry for the + * specified host, port, scheme and realm exists then this does nothing. + * * @param auth_info the AuthorizationInfo to remove * @param context the context this info is associated with */ @@ -561,6 +589,7 @@ * Removes an authorization entry from the list using the default conte= xt. If * no entry for the specified host, port, scheme and realm exists then = this * does nothing. + * * @param host the host * @param port the port * @param scheme the scheme @@ -572,8 +601,9 @@ } = /** - * Removes an authorization entry from the list. If no entry for the sp= ecified - * host, port, scheme and realm exists then this does nothing. + * Removes an authorization entry from the list. If no entry for the + * specified host, port, scheme and realm exists then this does nothing. + * * @param host the host * @param port the port * @param scheme the scheme @@ -587,9 +617,10 @@ = /** * Tries to find the candidate in the current list of auth info for the= given - * request. The paths associated with each auth info are examined, and = the one - * with either the nearest direct parent or child is chosen. This is us= ed for - * preemptively sending auth info. + * request. The paths associated with each auth info are examined, and = the + * one with either the nearest direct parent or child is chosen. This i= s used + * for preemptively sending auth info. + * * @param req the Request * @return an AuthorizationInfo containing the info for the best match,= or * null if none found. @@ -675,6 +706,7 @@ /** * Adds the path from the given resource to our path list. The path lis= t is * used for deciding when to preemptively send auth info. + * * @param resource the resource from which to extract the path */ public synchronized void addPath(String resource) @@ -692,11 +724,12 @@ } = /** - * Parses the authentication challenge(s) into an array of new info str= uctures - * for the specified host and port. - * @param challenge a string containing authentication info. This must = have the - * same format as value part of a WWW-authenticate response he= ader - * field, and may contain multiple authentication challenges. + * Parses the authentication challenge(s) into an array of new info + * structures for the specified host and port. + * + * @param challenge a string containing authentication info. This must = have + * the same format as value part of a WWW-authenticate response = header + * field, and may contain multiple authentication challenges. * @param req the original request. * @exception ProtocolException if any error during the parsing occurs. */ @@ -887,6 +920,7 @@ = /** * Get the host. + * * @return a string containing the host name. */ public final String getHost() @@ -896,6 +930,7 @@ = /** * Get the port. + * * @return an int containing the port number. */ public final int getPort() @@ -905,6 +940,7 @@ = /** * Get the scheme. + * * @return a string containing the scheme. */ public final String getScheme() @@ -914,6 +950,7 @@ = /** * Get the realm. + * * @return a string containing the realm. */ public final String getRealm() @@ -923,6 +960,7 @@ = /** * Get the cookie + * * @return the cookie String * @since V0.3-1 */ @@ -933,6 +971,7 @@ = /** * Set the cookie + * * @param cookie the new cookie * @since V0.3-1 */ @@ -943,6 +982,7 @@ = /** * Get the authentication parameters. + * * @return an array of name/value pairs. */ public final NVPair[] getParams() @@ -952,6 +992,7 @@ = /** * Set the authentication parameters. + * * @param an array of name/value pairs. */ public final void setParams(NVPair[] params) @@ -964,6 +1005,7 @@ = /** * Get the extra info. + * * @return the extra_info object */ public final Object getExtraInfo() @@ -973,6 +1015,7 @@ = /** * Set the extra info. + * * @param info the extra info */ public final void setExtraInfo(Object info) @@ -983,6 +1026,7 @@ /** * Constructs a string containing the authorization info. The format is= that * of the http Authorization header. + * * @return a String containing all info. */ public String toString() @@ -1025,6 +1069,7 @@ * Produces a hash code based on host, scheme and realm. Port is not in= cluded * for simplicity (and because it probably won't make much difference).= Used * in the AuthorizationInfo.AuthList hash table. + * * @return the hash code */ public int hashCode() @@ -1033,10 +1078,11 @@ } = /** - * Two AuthorizationInfos are considered equal if their host, port, sch= eme and - * realm match. Used in the AuthorizationInfo.AuthList hash table. + * Two AuthorizationInfos are considered equal if their host, port, sch= eme + * and realm match. Used in the AuthorizationInfo.AuthList hash table. + * * @param obj another AuthorizationInfo against which this one is to be - * compared. + * compared. * @return true if they match in the above mentioned fields; false othe= rwise. */ public boolean equals(Object obj) @@ -1045,7 +1091,7 @@ { AuthorizationInfo auth =3D (AuthorizationInfo)obj; if (host.equals(auth.host) && (port =3D=3D auth.port) && scheme.e= qualsIgnoreCase(auth.scheme) - && realm.equals(auth.realm)) + && ((realm =3D=3D null && auth.realm =3D=3D null) || (realm != =3D null && realm.equals(auth.realm)))) return true; } return false; Modified: ws/trunk/exo.ws.rest.ext/src/main/java/org/exoplatform/services/r= est/ext/proxy/ProxyService.java =3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D= =3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D= =3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D --- ws/trunk/exo.ws.rest.ext/src/main/java/org/exoplatform/services/rest/ex= t/proxy/ProxyService.java 2010-06-25 14:51:32 UTC (rev 2710) +++ ws/trunk/exo.ws.rest.ext/src/main/java/org/exoplatform/services/rest/ex= t/proxy/ProxyService.java 2010-06-29 10:35:54 UTC (rev 2711) @@ -18,11 +18,27 @@ */ package org.exoplatform.services.rest.ext.proxy; = +import org.exoplatform.common.http.client.HTTPConnection; +import org.exoplatform.common.http.client.HTTPResponse; +import org.exoplatform.common.http.client.HttpOutputStream; +import org.exoplatform.common.http.client.ModuleException; +import org.exoplatform.common.http.client.NVPair; +import org.exoplatform.common.http.client.ProtocolNotSuppException; +import org.exoplatform.services.log.ExoLogger; +import org.exoplatform.services.log.Log; +import org.exoplatform.services.rest.resource.ResourceContainer; + import java.io.IOException; +import java.io.InputStream; import java.net.MalformedURLException; +import java.net.URL; +import java.util.ArrayList; +import java.util.Collections; import java.util.Enumeration; +import java.util.List; +import java.util.Set; +import java.util.Map.Entry; = -import javax.servlet.http.HttpServletRequest; import javax.ws.rs.DELETE; import javax.ws.rs.GET; import javax.ws.rs.POST; @@ -31,15 +47,12 @@ import javax.ws.rs.QueryParam; import javax.ws.rs.WebApplicationException; import javax.ws.rs.core.Context; +import javax.ws.rs.core.HttpHeaders; +import javax.ws.rs.core.MultivaluedMap; import javax.ws.rs.core.Response; +import javax.ws.rs.core.UriInfo; import javax.ws.rs.core.Response.ResponseBuilder; = -import org.exoplatform.common.http.client.HTTPResponse; -import org.exoplatform.common.http.client.ModuleException; -import org.exoplatform.common.http.client.ParseException; -import org.exoplatform.common.http.client.ProtocolNotSuppException; -import org.exoplatform.services.rest.resource.ResourceContainer; - /** * @author Max Shaposh= nik * @version $Id$ @@ -47,25 +60,42 @@ @Path("proxy") public class ProxyService implements ResourceContainer { - /** - * Handles GET proxy request. - * = - * @param httpRequestHttpServletRequest - * @param url the url to request - * @return response Response - */ - @GET - public Response doProxyGet(@Context HttpServletRequest httpRequest, @Qu= eryParam("url") String url) + protected static final int DEFAULT_CONNECT_TIMEOUT_MS =3D 5000; + + private static final Log LOG =3D ExoLogger.getLogger(ProxyService.class= ); + + @DELETE + public Response doProxyDelete(@Context HttpHeaders headers, @Context Ur= iInfo uriInfo, + @QueryParam("url") String urlParam) { - BaseConnector conn =3D new BaseConnector(); - if (url =3D=3D null) + if (urlParam =3D=3D null) { - Throwable e =3D new Throwable("Necessary URL parameter not found = in proxy request"); + IllegalArgumentException e =3D new IllegalArgumentException("'url= ' parameter not found in proxy request"); throw new WebApplicationException(e, createErrorResponse(e, 404)); } try { - HTTPResponse resp =3D conn.fetchGet(httpRequest, url); + URL url =3D new URL(urlParam); + HTTPConnection conn =3D new HTTPConnection(url); + conn.setTimeout(DEFAULT_CONNECT_TIMEOUT_MS); + NVPair[] headerPairs =3D + toNVPair(headers.getRequestHeaders(), Collections.singleton(Ht= tpHeaders.HOST.toLowerCase())); + conn.setAllowUserInteraction(false); + NVPair credentials =3D getCredentials(url); + if (credentials !=3D null) + { + conn.addBasicAuthorization(null, credentials.getName(), creden= tials.getValue()); + } + HTTPResponse resp =3D conn.Delete(url.getFile(), headerPairs); + if (resp.getStatusCode() >=3D 300) + { + LOG.warn("DELETE Received : " + resp.getReasonLine()); + byte[] data =3D resp.getData(); + if (data !=3D null) + { + LOG.warn("DELETE Received : " + new String(data)); + } + } return createResponse(resp); } catch (MalformedURLException mue) @@ -84,32 +114,39 @@ { throw new WebApplicationException(me, createErrorResponse(me, 500= )); } - catch (ParseException pe) - { - throw new WebApplicationException(pe, createErrorResponse(pe, 400= )); - } - } = - /** - * Handles POST proxy request. - * = - * @param httpRequestHttpServletRequest - * @param url the url to request - * @return response Response - */ - @POST - public Response doProxyPost(@Context HttpServletRequest httpRequest, @Q= ueryParam("url") String url) + @GET + public Response doProxyGet(@Context HttpHeaders headers, @Context UriIn= fo uriInfo, @QueryParam("url") String urlParam) { - BaseConnector conn =3D new BaseConnector(); - if (url =3D=3D null) + if (urlParam =3D=3D null) { - Throwable e =3D new Throwable("Necessary URL parameter not found = in proxy request"); + IllegalArgumentException e =3D new IllegalArgumentException("'url= ' parameter not found in proxy request"); throw new WebApplicationException(e, createErrorResponse(e, 404)); } try { - HTTPResponse resp =3D conn.fetchPost(httpRequest, url); + URL url =3D new URL(urlParam); + HTTPConnection conn =3D new HTTPConnection(url); + conn.setTimeout(DEFAULT_CONNECT_TIMEOUT_MS); + NVPair[] headerPairs =3D + toNVPair(headers.getRequestHeaders(), Collections.singleton(Ht= tpHeaders.HOST.toLowerCase())); + conn.setAllowUserInteraction(false); + NVPair credentials =3D getCredentials(url); + if (credentials !=3D null) + { + conn.addBasicAuthorization(null, credentials.getName(), creden= tials.getValue()); + } + HTTPResponse resp =3D conn.Get(url.getFile(), (NVPair[])null, hea= derPairs); + if (resp.getStatusCode() >=3D 300) + { + LOG.warn("GET Received: " + resp.getReasonLine()); + byte[] data =3D resp.getData(); + if (data !=3D null) + { + LOG.warn("GET Received: " + new String(data)); + } + } return createResponse(resp); } catch (MalformedURLException mue) @@ -128,31 +165,58 @@ { throw new WebApplicationException(me, createErrorResponse(me, 500= )); } - catch (ParseException pe) - { - throw new WebApplicationException(pe, createErrorResponse(pe, 400= )); - } } = - /** - * Handles PUT proxy request. - * = - * @param httpRequestHttpServletRequest - * @param url the url to request - * @return response Response - */ - @PUT - public Response doProxyPut(@Context HttpServletRequest httpRequest, @Qu= eryParam("url") String url) + @POST + public Response doProxyPost(@Context HttpHeaders headers, @Context UriI= nfo uriInfo, + @QueryParam("url") String urlParam, InputStream entity) { - BaseConnector conn =3D new BaseConnector(); - if (url =3D=3D null) + if (urlParam =3D=3D null) { - Throwable e =3D new Throwable("Necessary URL parameter not found = in proxy request"); + IllegalArgumentException e =3D new IllegalArgumentException("'url= ' parameter not found in proxy request"); throw new WebApplicationException(e, createErrorResponse(e, 404)); } + try { - HTTPResponse resp =3D conn.doPut(httpRequest, url); + URL url =3D new URL(urlParam); + HTTPConnection conn =3D new HTTPConnection(url); + conn.setTimeout(DEFAULT_CONNECT_TIMEOUT_MS); + NVPair[] headerPairs =3D + toNVPair(headers.getRequestHeaders(), Collections.singleton(Ht= tpHeaders.HOST.toLowerCase())); + conn.setAllowUserInteraction(false); + NVPair credentials =3D getCredentials(url); + if (credentials !=3D null) + { + conn.addBasicAuthorization(null, credentials.getName(), creden= tials.getValue()); + } + HTTPResponse resp =3D null; + if (entity !=3D null) + { + HttpOutputStream stream =3D new HttpOutputStream(); + resp =3D conn.Post(url.getFile(), stream, headerPairs); + byte[] buf =3D new byte[1024]; + int r =3D -1; + while ((r =3D entity.read()) !=3D -1) + { + stream.write(buf, 0, r); + } + stream.close(); + } + else + { + resp =3D conn.Post(url.getFile(), (NVPair[])null, headerPairs); + } + + if (resp.getStatusCode() >=3D 300) + { + LOG.warn("POST Received: " + resp.getReasonLine()); + byte[] data =3D resp.getData(); + if (data !=3D null) + { + LOG.warn("POST Received: " + new String(data)); + } + } return createResponse(resp); } catch (MalformedURLException mue) @@ -171,32 +235,58 @@ { throw new WebApplicationException(me, createErrorResponse(me, 500= )); } - catch (ParseException pe) - { - throw new WebApplicationException(pe, createErrorResponse(pe, 400= )); - } - } = - /** - * Handles DELETE proxy request. - * = - * @param httpRequestHttpServletRequest - * @param url the url to request - * @return response Response - */ - @DELETE - public Response doProxyDelete(@Context HttpServletRequest httpRequest, = @QueryParam("url") String url) + @PUT + public Response doProxyPut(@Context HttpHeaders headers, @Context UriIn= fo uriInfo, + @QueryParam("url") String urlParam, InputStream entity) { - BaseConnector conn =3D new BaseConnector(); - if (url =3D=3D null) + if (urlParam =3D=3D null) { - Throwable e =3D new Throwable("Necessary URL parameter not found = in proxy request"); + IllegalArgumentException e =3D new IllegalArgumentException("'url= ' parameter not found in proxy request"); throw new WebApplicationException(e, createErrorResponse(e, 404)); } + try { - HTTPResponse resp =3D conn.doDelete(httpRequest, url); + URL url =3D new URL(urlParam); + HTTPConnection conn =3D new HTTPConnection(url); + conn.setTimeout(DEFAULT_CONNECT_TIMEOUT_MS); + NVPair[] headerPairs =3D + toNVPair(headers.getRequestHeaders(), Collections.singleton(Ht= tpHeaders.HOST.toLowerCase())); + conn.setAllowUserInteraction(false); + NVPair credentials =3D getCredentials(url); + if (credentials !=3D null) + { + conn.addBasicAuthorization(null, credentials.getName(), creden= tials.getValue()); + } + HTTPResponse resp =3D null; + if (entity !=3D null) + { + HttpOutputStream stream =3D new HttpOutputStream(); + resp =3D conn.Put(url.getFile(), stream, headerPairs); + byte[] buf =3D new byte[1024]; + int r =3D -1; + while ((r =3D entity.read()) !=3D -1) + { + stream.write(buf, 0, r); + } + stream.close(); + } + else + { + resp =3D conn.Put(url.getFile(), new byte[0], headerPairs); + } + + if (resp.getStatusCode() >=3D 300) + { + LOG.warn("PUT Received : " + resp.getReasonLine()); + byte[] data =3D resp.getData(); + if (data !=3D null) + { + LOG.warn("PUT Received : " + new String(data)); + } + } return createResponse(resp); } catch (MalformedURLException mue) @@ -215,16 +305,23 @@ { throw new WebApplicationException(me, createErrorResponse(me, 500= )); } - catch (ParseException pe) - { - throw new WebApplicationException(pe, createErrorResponse(pe, 400= )); - } + } = + /** + * Creates the error response. + * + * @param t Throwable + * @param status integer response status + * @return response Response + */ + private Response createErrorResponse(Throwable t, int status) + { + return Response.status(status).entity(t.getMessage()).type("text/pla= in").build(); } = /** * Creates the response from HTTP response. - * = + * * @param httpResponse the http response * @return response Response */ @@ -236,7 +333,7 @@ responseBuilder =3D Response.status(httpResponse.getStatusCode()); for (Enumeration en =3D httpResponse.listHeaders(); en.ha= sMoreElements();) { - String headerName =3D (String)en.nextElement(); + String headerName =3D en.nextElement(); responseBuilder.header(headerName, httpResponse.getHeader(head= erName)); } return responseBuilder.entity(httpResponse.getInputStream()).buil= d(); @@ -251,15 +348,42 @@ } } = - /** - * Creates the error response. - * = - * @param t Throwable - * @param status integer response status - * @return response Response - */ - private Response createErrorResponse(Throwable t, int status) + private NVPair getCredentials(URL url) { - return Response.status(status).entity(t.getMessage()).type("text/pla= in").build(); + String userInfo =3D url.getUserInfo(); + NVPair credentials =3D null; + if (userInfo !=3D null) + { + int col =3D userInfo.indexOf(':'); + if (col =3D=3D -1) + { + credentials =3D new NVPair(userInfo, ""); + } + else if (col =3D=3D userInfo.length() - 1) + { + credentials =3D new NVPair(userInfo.substring(0, userInfo.leng= th() - 1), ""); + } + else + { + credentials =3D new NVPair(userInfo.substring(0, col), userInf= o.substring(col + 1)); + } + } + return credentials; } + + private NVPair[] toNVPair(MultivaluedMap map, Set skip) + { + List hds =3D new ArrayList(); + for (Entry> e : map.entrySet()) + { + if (!skip.contains(e.getKey())) + { + for (String v : e.getValue()) + { + hds.add(new NVPair(e.getKey(), v)); + } + } + } + return hds.toArray(new NVPair[hds.size()]); + } } --===============3672290304436851655==--