View Javadoc

1   /**
2    * Licensed to jclouds, Inc. (jclouds) under one or more
3    * contributor license agreements.  See the NOTICE file
4    * distributed with this work for additional information
5    * regarding copyright ownership.  jclouds licenses this file
6    * to you under the Apache License, Version 2.0 (the
7    * "License"); you may not use this file except in compliance
8    * with the License.  You may obtain a copy of the License at
9    *
10   *   http://www.apache.org/licenses/LICENSE-2.0
11   *
12   * Unless required by applicable law or agreed to in writing,
13   * software distributed under the License is distributed on an
14   * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
15   * KIND, either express or implied.  See the License for the
16   * specific language governing permissions and limitations
17   * under the License.
18   */
19  package org.jclouds.http.apachehc;
20  
21  import java.io.File;
22  import java.io.IOException;
23  import java.io.InputStream;
24  import java.io.OutputStream;
25  import java.io.UnsupportedEncodingException;
26  
27  import javax.inject.Singleton;
28  import javax.ws.rs.HttpMethod;
29  import javax.ws.rs.core.HttpHeaders;
30  
31  import org.apache.http.HttpEntity;
32  import org.apache.http.HttpEntityEnclosingRequest;
33  import org.apache.http.client.methods.HttpDelete;
34  import org.apache.http.client.methods.HttpEntityEnclosingRequestBase;
35  import org.apache.http.client.methods.HttpGet;
36  import org.apache.http.client.methods.HttpHead;
37  import org.apache.http.client.methods.HttpPost;
38  import org.apache.http.client.methods.HttpPut;
39  import org.apache.http.client.methods.HttpRequestBase;
40  import org.apache.http.client.methods.HttpUriRequest;
41  import org.apache.http.entity.ByteArrayEntity;
42  import org.apache.http.entity.FileEntity;
43  import org.apache.http.entity.InputStreamEntity;
44  import org.apache.http.entity.StringEntity;
45  import org.apache.http.params.CoreProtocolPNames;
46  import org.jclouds.http.HttpRequest;
47  import org.jclouds.io.Payload;
48  import org.jclouds.io.payloads.BasePayload;
49  import org.jclouds.io.payloads.ByteArrayPayload;
50  import org.jclouds.io.payloads.DelegatingPayload;
51  import org.jclouds.io.payloads.FilePayload;
52  import org.jclouds.io.payloads.StringPayload;
53  
54  import com.google.common.base.Throwables;
55  
56  /**
57   * 
58   * @author Adrian Cole
59   */
60  @Singleton
61  public class ApacheHCUtils {
62  
63     public static final String USER_AGENT = "jclouds/1.0 httpclient/4.0.1";
64  
65     public static HttpUriRequest convertToApacheRequest(HttpRequest request) {
66        HttpUriRequest apacheRequest;
67        if (request.getMethod().equals(HttpMethod.HEAD)) {
68           apacheRequest = new HttpHead(request.getEndpoint());
69        } else if (request.getMethod().equals(HttpMethod.GET)) {
70           apacheRequest = new HttpGet(request.getEndpoint());
71        } else if (request.getMethod().equals(HttpMethod.DELETE)) {
72           apacheRequest = new HttpDelete(request.getEndpoint());
73        } else if (request.getMethod().equals(HttpMethod.PUT)) {
74           apacheRequest = new HttpPut(request.getEndpoint());
75           apacheRequest.getParams().setBooleanParameter(CoreProtocolPNames.USE_EXPECT_CONTINUE, true);
76        } else if (request.getMethod().equals(HttpMethod.POST)) {
77           apacheRequest = new HttpPost(request.getEndpoint());
78        } else {
79           final String method = request.getMethod();
80           if (request.getPayload() != null)
81              apacheRequest = new HttpEntityEnclosingRequestBase() {
82  
83                 @Override
84                 public String getMethod() {
85                    return method;
86                 }
87  
88              };
89           else
90              apacheRequest = new HttpRequestBase() {
91  
92                 @Override
93                 public String getMethod() {
94                    return method;
95                 }
96  
97              };
98           HttpRequestBase.class.cast(apacheRequest).setURI(request.getEndpoint());
99        }
100       Payload payload = request.getPayload();
101 
102       // Since we may remove headers, ensure they are added to the apache
103       // request after this block
104       if (apacheRequest instanceof HttpEntityEnclosingRequest) {
105          if (payload != null) {
106             addEntityForContent(HttpEntityEnclosingRequest.class.cast(apacheRequest), payload);
107          }
108       } else {
109          apacheRequest.addHeader(HttpHeaders.CONTENT_LENGTH, "0");
110       }
111 
112       for (String header : request.getHeaders().keySet()) {
113          for (String value : request.getHeaders().get(header))
114             // apache automatically tries to add content length header
115             if (!header.equals(HttpHeaders.CONTENT_LENGTH))
116                apacheRequest.addHeader(header, value);
117       }
118       apacheRequest.addHeader(HttpHeaders.USER_AGENT, USER_AGENT);
119       return apacheRequest;
120    }
121 
122    public static void addEntityForContent(HttpEntityEnclosingRequest apacheRequest, Payload payload) {
123       payload = payload instanceof DelegatingPayload ? DelegatingPayload.class.cast(payload).getDelegate() : payload;
124       if (payload instanceof StringPayload) {
125          StringEntity nStringEntity = null;
126          try {
127             nStringEntity = new StringEntity((String) payload.getRawContent());
128          } catch (UnsupportedEncodingException e) {
129             throw new UnsupportedOperationException("Encoding not supported", e);
130          }
131          nStringEntity.setContentType(payload.getContentMetadata().getContentType());
132          apacheRequest.setEntity(nStringEntity);
133       } else if (payload instanceof FilePayload) {
134          apacheRequest.setEntity(new FileEntity((File) payload.getRawContent(), payload.getContentMetadata()
135                .getContentType()));
136       } else if (payload instanceof ByteArrayPayload) {
137          ByteArrayEntity Entity = new ByteArrayEntity((byte[]) payload.getRawContent());
138          Entity.setContentType(payload.getContentMetadata().getContentType());
139          apacheRequest.setEntity(Entity);
140       } else {
141          InputStream inputStream = payload.getInput();
142          if (payload.getContentMetadata().getContentLength() == null)
143             throw new IllegalArgumentException("you must specify size when content is an InputStream");
144          InputStreamEntity Entity = new InputStreamEntity(inputStream, payload.getContentMetadata().getContentLength());
145          Entity.setContentType(payload.getContentMetadata().getContentType());
146          apacheRequest.setEntity(Entity);
147       }
148       if (payload.getContentMetadata().getContentDisposition() != null)
149          apacheRequest.addHeader("Content-Disposition", payload.getContentMetadata().getContentDisposition());
150       if (payload.getContentMetadata().getContentEncoding() != null)
151          apacheRequest.addHeader("Content-Encoding", payload.getContentMetadata().getContentEncoding());
152       if (payload.getContentMetadata().getContentLanguage() != null)
153          apacheRequest.addHeader("Content-Language", payload.getContentMetadata().getContentLanguage());
154       assert (apacheRequest.getEntity() != null);
155    }
156 
157    public static class HttpEntityPayload extends BasePayload<HttpEntity> {
158 
159       HttpEntityPayload(HttpEntity content) {
160          super(content);
161          getContentMetadata().setContentType(content.getContentType().getValue());
162          getContentMetadata().setContentLength(content.getContentLength());
163       }
164 
165       @Override
166       public InputStream getInput() {
167          try {
168             return content.getContent();
169          } catch (IllegalStateException e) {
170             Throwables.propagate(e);
171          } catch (IOException e) {
172             Throwables.propagate(e);
173          }
174          return null;
175       }
176 
177       @Override
178       public boolean isRepeatable() {
179          return content.isRepeatable();
180       }
181 
182       @Override
183       public void release() {
184          try {
185             content.consumeContent();
186          } catch (IOException e) {
187          }
188       }
189 
190       @Override
191       public void writeTo(OutputStream outstream) throws IOException {
192          super.writeTo(outstream);
193       }
194 
195    }
196 
197 }