1   /*
2    * $HeadURL: http://svn.apache.org/repos/asf/jakarta/commons/proper/httpclient/trunk/src/test/org/apache/commons/httpclient/TestEntityEnclosingMethod.java $
3    * $Revision: 201849 $
4    * $Date: 2005-06-26 09:26:59 -0400 (Sun, 26 Jun 2005) $
5    *
6    * ====================================================================
7    *
8    *  Copyright 2003-2004 The Apache Software Foundation
9    *
10   *  Licensed under the Apache License, Version 2.0 (the "License");
11   *  you may not use this file except in compliance with the License.
12   *  You may obtain a copy of the License at
13   *
14   *      http://www.apache.org/licenses/LICENSE-2.0
15   *
16   *  Unless required by applicable law or agreed to in writing, software
17   *  distributed under the License is distributed on an "AS IS" BASIS,
18   *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
19   *  See the License for the specific language governing permissions and
20   *  limitations under the License.
21   * ====================================================================
22   *
23   * This software consists of voluntary contributions made by many
24   * individuals on behalf of the Apache Software Foundation.  For more
25   * information on the Apache Software Foundation, please see
26   * <http://www.apache.org/>.
27   *
28   */
29  
30  package org.apache.commons.httpclient;
31  
32  import java.io.ByteArrayInputStream;
33  import java.io.IOException;
34  import java.io.InputStream;
35  
36  import junit.framework.Test;
37  import junit.framework.TestSuite;
38  
39  import org.apache.commons.httpclient.auth.AuthScope;
40  import org.apache.commons.httpclient.methods.InputStreamRequestEntity;
41  import org.apache.commons.httpclient.methods.PostMethod;
42  import org.apache.commons.httpclient.methods.RequestEntity;
43  import org.apache.commons.httpclient.methods.StringRequestEntity;
44  import org.apache.commons.httpclient.server.AuthRequestHandler;
45  import org.apache.commons.httpclient.server.HttpRequestHandlerChain;
46  import org.apache.commons.httpclient.server.HttpService;
47  import org.apache.commons.httpclient.server.HttpServiceHandler;
48  import org.apache.commons.httpclient.server.SimpleRequest;
49  import org.apache.commons.httpclient.server.SimpleResponse;
50  
51  /***
52   * Tests specific to entity enclosing methods.
53   *
54   * @author Oleg Kalnichevski
55   * @version $Id: TestEntityEnclosingMethod.java 201849 2005-06-26 13:26:59Z olegk $
56   */
57  public class TestEntityEnclosingMethod extends HttpClientTestBase {
58  
59      public TestEntityEnclosingMethod(String testName) throws IOException {
60          super(testName);
61      }
62  
63      public static Test suite() {
64          TestSuite suite = new TestSuite(TestEntityEnclosingMethod.class);
65          return suite;
66      }
67  
68      public static void main(String args[]) {
69          String[] testCaseName = { TestEntityEnclosingMethod.class.getName() };
70          junit.textui.TestRunner.main(testCaseName);
71      }
72  
73      // ------------------------------------------------------------------ Tests
74      
75      public void testEnclosedEntityAutoLength() throws Exception {
76          String inputstr = "This is a test message";
77          byte[] input = inputstr.getBytes("US-ASCII");
78          InputStream instream = new ByteArrayInputStream(input);
79          
80          RequestEntity requestentity = new InputStreamRequestEntity(
81                  instream, InputStreamRequestEntity.CONTENT_LENGTH_AUTO); 
82          PostMethod method = new PostMethod("/");
83          method.setRequestEntity(requestentity);
84          this.server.setHttpService(new EchoService());
85          try {
86              this.client.executeMethod(method);
87              assertEquals(200, method.getStatusCode());
88              String body = method.getResponseBodyAsString();
89              assertEquals(inputstr, body);
90              assertNull(method.getRequestHeader("Transfer-Encoding"));
91              assertNotNull(method.getRequestHeader("Content-Length"));
92              assertEquals(input.length, Integer.parseInt(
93                      method.getRequestHeader("Content-Length").getValue()));
94          } finally {
95              method.releaseConnection();
96          }
97      }
98  
99      public void testEnclosedEntityExplicitLength() throws Exception {
100         String inputstr = "This is a test message";
101         byte[] input = inputstr.getBytes("US-ASCII");
102         InputStream instream = new ByteArrayInputStream(input);
103         
104         RequestEntity requestentity = new InputStreamRequestEntity(
105                 instream, 14); 
106         PostMethod method = new PostMethod("/");
107         method.setRequestEntity(requestentity);
108         this.server.setHttpService(new EchoService());
109         try {
110             this.client.executeMethod(method);
111             assertEquals(200, method.getStatusCode());
112             String body = method.getResponseBodyAsString();
113             assertEquals("This is a test", body);
114             assertNull(method.getRequestHeader("Transfer-Encoding"));
115             assertNotNull(method.getRequestHeader("Content-Length"));
116             assertEquals(14, Integer.parseInt(
117                     method.getRequestHeader("Content-Length").getValue()));
118         } finally {
119             method.releaseConnection();
120         }
121     }
122 
123     public void testEnclosedEntityChunked() throws Exception {
124         String inputstr = "This is a test message";
125         byte[] input = inputstr.getBytes("US-ASCII");
126         InputStream instream = new ByteArrayInputStream(input);
127         
128         RequestEntity requestentity = new InputStreamRequestEntity(
129                 instream, InputStreamRequestEntity.CONTENT_LENGTH_AUTO); 
130         PostMethod method = new PostMethod("/");
131         method.setRequestEntity(requestentity);
132         method.setContentChunked(true);
133         this.server.setHttpService(new EchoService());
134         try {
135             this.client.executeMethod(method);
136             assertEquals(200, method.getStatusCode());
137             String body = method.getResponseBodyAsString();
138             assertEquals(inputstr, body);
139             assertNotNull(method.getRequestHeader("Transfer-Encoding"));
140             assertNull(method.getRequestHeader("Content-Length"));
141         } finally {
142             method.releaseConnection();
143         }
144     }
145     
146     public void testEnclosedEntityChunkedHTTP1_0() throws Exception {
147         String inputstr = "This is a test message";
148         byte[] input = inputstr.getBytes("US-ASCII");
149         InputStream instream = new ByteArrayInputStream(input);
150         
151         RequestEntity requestentity = new InputStreamRequestEntity(
152                 instream, InputStreamRequestEntity.CONTENT_LENGTH_AUTO); 
153         PostMethod method = new PostMethod("/");
154         method.setRequestEntity(requestentity);
155         method.setContentChunked(true);
156         method.getParams().setVersion(HttpVersion.HTTP_1_0);
157         this.server.setHttpService(new EchoService());
158         try {
159             this.client.executeMethod(method);
160             fail("ProtocolException should have been thrown");
161         } catch (ProtocolException ex) {
162             // expected
163         } finally {
164             method.releaseConnection();
165         }
166     }
167 
168     public void testEnclosedEntityRepeatable() throws Exception {
169         String inputstr = "This is a test message";
170         byte[] input = inputstr.getBytes("US-ASCII");
171         InputStream instream = new ByteArrayInputStream(input);
172         
173         RequestEntity requestentity = new InputStreamRequestEntity(
174                 instream, InputStreamRequestEntity.CONTENT_LENGTH_AUTO); 
175         PostMethod method = new PostMethod("/");
176         method.setRequestEntity(requestentity);
177 
178         UsernamePasswordCredentials creds = 
179             new UsernamePasswordCredentials("testuser", "testpass");
180         
181         HttpRequestHandlerChain handlerchain = new HttpRequestHandlerChain();
182         handlerchain.appendHandler(new AuthRequestHandler(creds));
183         handlerchain.appendHandler(new HttpServiceHandler(new EchoService()));
184         this.server.setRequestHandler(handlerchain);
185         this.client.getState().setCredentials(AuthScope.ANY, creds);
186         try {
187             this.client.executeMethod(method);
188             assertEquals(200, method.getStatusCode());
189             String body = method.getResponseBodyAsString();
190             assertEquals(inputstr, body);
191             assertNull(method.getRequestHeader("Transfer-Encoding"));
192             assertNotNull(method.getRequestHeader("Content-Length"));
193             assertEquals(input.length, Integer.parseInt(
194                     method.getRequestHeader("Content-Length").getValue()));
195         } finally {
196             method.releaseConnection();
197         }
198     }
199 
200     public void testEnclosedEntityNonRepeatable() throws Exception {
201         String inputstr = "This is a test message";
202         byte[] input = inputstr.getBytes("US-ASCII");
203         InputStream instream = new ByteArrayInputStream(input);
204         
205         RequestEntity requestentity = new InputStreamRequestEntity(
206                 instream, InputStreamRequestEntity.CONTENT_LENGTH_AUTO); 
207         PostMethod method = new PostMethod("/");
208         method.setRequestEntity(requestentity);
209         method.setContentChunked(true);
210 
211         UsernamePasswordCredentials creds = 
212             new UsernamePasswordCredentials("testuser", "testpass");
213         
214         HttpRequestHandlerChain handlerchain = new HttpRequestHandlerChain();
215         handlerchain.appendHandler(new AuthRequestHandler(creds));
216         handlerchain.appendHandler(new HttpServiceHandler(new EchoService()));
217         this.server.setRequestHandler(handlerchain);
218         this.client.getState().setCredentials(AuthScope.ANY, creds);
219         try {
220             this.client.executeMethod(method);
221             fail("ProtocolException should have been thrown");
222         } catch (ProtocolException ex) {
223             // expected
224         } finally {
225             method.releaseConnection();
226         }
227     }
228     
229     public void testEnclosedEntityNegativeLength() throws Exception {
230         
231         String inputstr = "This is a test message";
232         byte[] input = inputstr.getBytes("US-ASCII");
233         InputStream instream = new ByteArrayInputStream(input);
234         
235         RequestEntity requestentity = new InputStreamRequestEntity(
236                 instream, -14); 
237         PostMethod method = new PostMethod("/");
238         method.setRequestEntity(requestentity);
239         method.setContentChunked(false);
240         this.server.setHttpService(new EchoService());
241         try {
242             this.client.executeMethod(method);
243             assertEquals(200, method.getStatusCode());
244             String body = method.getResponseBodyAsString();
245             assertEquals(inputstr, body);
246             assertNotNull(method.getRequestHeader("Transfer-Encoding"));
247             assertNull(method.getRequestHeader("Content-Length"));
248         } finally {
249             method.releaseConnection();
250         }
251     }
252 
253     public void testEnclosedEntityNegativeLengthHTTP1_0() throws Exception {
254         
255         String inputstr = "This is a test message";
256         byte[] input = inputstr.getBytes("US-ASCII");
257         InputStream instream = new ByteArrayInputStream(input);
258         
259         RequestEntity requestentity = new InputStreamRequestEntity(
260                 instream, -14); 
261         PostMethod method = new PostMethod("/");
262         method.setRequestEntity(requestentity);
263         method.setContentChunked(false);
264         method.getParams().setVersion(HttpVersion.HTTP_1_0);
265         this.server.setHttpService(new EchoService());
266         try {
267             this.client.executeMethod(method);
268             fail("ProtocolException should have been thrown");
269         } catch (ProtocolException ex) {
270             // expected
271         } finally {
272             method.releaseConnection();
273         }
274     }
275     
276     class RequestBodyStatsService implements HttpService {
277 
278         public RequestBodyStatsService() {
279             super();
280         }
281 
282         public boolean process(final SimpleRequest request, final SimpleResponse response)
283             throws IOException
284         {
285             HttpVersion httpversion = request.getRequestLine().getHttpVersion();
286             response.setStatusLine(httpversion, HttpStatus.SC_OK);
287             response.addHeader(new Header("Content-Type", "text/plain"));            
288 
289             StringBuffer buffer = new StringBuffer();
290             buffer.append("Request bosy stats:\r\n");
291             buffer.append("===================\r\n");
292             long l = request.getContentLength();
293             if (l >= 0) {
294                 buffer.append("Content-Length: ");
295                 buffer.append(l);
296                 buffer.append("\r\n");
297             }
298             Header te = request.getFirstHeader("Transfer-Encoding");
299             if (te != null) {
300                 buffer.append("Content-Length: ");
301                 buffer.append(te.getValue());
302                 buffer.append("\r\n");
303             }
304             byte[] b = request.getBodyBytes();
305             if (b.length <= 0) {
306                 buffer.append("No body submitted\r\n");
307             }
308             response.setBodyString(buffer.toString());
309             return true;
310         }
311     }
312 	
313     public void testEmptyPostMethod() throws Exception {
314         this.server.setHttpService(new RequestBodyStatsService());
315 
316         PostMethod method = new PostMethod("/");
317         method.setRequestHeader("Content-Type", "text/plain");
318         this.client.executeMethod(method);
319         assertEquals(200,method.getStatusLine().getStatusCode());
320         String response = method.getResponseBodyAsString();
321         assertNotNull(method.getRequestHeader("Content-Length"));
322         assertTrue(response.indexOf("No body submitted") >= 0);
323 
324         method = new PostMethod("/");
325         method.setRequestHeader("Content-Type", "text/plain");
326         method.setRequestEntity(new StringRequestEntity(""));
327 		this.client.executeMethod(method);
328         assertEquals(200,method.getStatusLine().getStatusCode());
329         assertNotNull(method.getRequestHeader("Content-Length"));
330         response = method.getResponseBodyAsString();
331         assertTrue(response.indexOf("No body submitted") >= 0);
332 
333         method = new PostMethod("/");
334         method.setRequestHeader("Content-Type", "text/plain");
335         method.setContentChunked(true);
336 		this.client.executeMethod(method);
337         assertEquals(200,method.getStatusLine().getStatusCode());
338         assertNotNull(method.getRequestHeader("Content-Length"));
339         response = method.getResponseBodyAsString();
340         assertTrue(response.indexOf("No body submitted") >= 0);
341 
342         method = new PostMethod("/");
343         method.setRequestHeader("Content-Type", "text/plain");
344         method.setRequestEntity(new StringRequestEntity(""));
345         method.setContentChunked(true);
346 		this.client.executeMethod(method);
347         assertNull(method.getRequestHeader("Content-Length"));
348         assertNotNull(method.getRequestHeader("Transfer-Encoding"));
349         assertEquals(200,method.getStatusLine().getStatusCode());
350         response = method.getResponseBodyAsString();
351         assertTrue(response.indexOf("No body submitted") >= 0);
352     }
353     
354 }
355