Author: markt
Date: Tue Jun 16 20:18:14 2009
New Revision: 785369

URL: http://svn.apache.org/viewvc?rev=785369&view=rev
Log:
Test case for bug 37794.
The generic code will move out of this class if it turns out to be useful for 
other test cases

Added:
    tomcat/trunk/test/org/apache/catalina/connector/
    tomcat/trunk/test/org/apache/catalina/connector/TestRequest.java   (with 
props)

Added: tomcat/trunk/test/org/apache/catalina/connector/TestRequest.java
URL: 
http://svn.apache.org/viewvc/tomcat/trunk/test/org/apache/catalina/connector/TestRequest.java?rev=785369&view=auto
==============================================================================
--- tomcat/trunk/test/org/apache/catalina/connector/TestRequest.java (added)
+++ tomcat/trunk/test/org/apache/catalina/connector/TestRequest.java Tue Jun 16 
20:18:14 2009
@@ -0,0 +1,299 @@
+/*
+ *  Licensed to the Apache Software Foundation (ASF) under one or more
+ *  contributor license agreements.  See the NOTICE file distributed with
+ *  this work for additional information regarding copyright ownership.
+ *  The ASF licenses this file to You under the Apache License, Version 2.0
+ *  (the "License"); you may not use this file except in compliance with
+ *  the License.  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ */
+
+package org.apache.catalina.connector;
+
+import java.io.BufferedReader;
+import java.io.IOException;
+import java.io.InputStream;
+import java.io.InputStreamReader;
+import java.io.OutputStream;
+import java.io.OutputStreamWriter;
+import java.io.PrintWriter;
+import java.io.Reader;
+import java.io.Writer;
+import java.net.Socket;
+import java.net.UnknownHostException;
+import java.util.ArrayList;
+import java.util.Enumeration;
+import java.util.List;
+
+import javax.servlet.ServletException;
+import javax.servlet.http.HttpServlet;
+import javax.servlet.http.HttpServletRequest;
+import javax.servlet.http.HttpServletResponse;
+
+import org.apache.catalina.core.StandardContext;
+import org.apache.catalina.startup.Tomcat;
+
+import junit.framework.TestCase;
+
+/**
+ * Test case for {...@link Request}. 
+ */
+public class TestRequest extends TestCase {
+    /**
+     * Test case for https://issues.apache.org/bugzilla/show_bug.cgi?id=37794
+     * POST parameters are not returned from a call to 
+     * any of the {...@link HttpServletRequest} getParameterXXX() methods.
+     * @throws Exception 
+     */
+    public void testBug37794() throws Exception {
+        Bug37794Client client = new Bug37794Client();
+
+        // Edge cases around zero
+        client.doRequest(-1); // Unlimited
+        assertTrue(client.isResponse200());
+        assertTrue(client.isResponseBodyOK());
+        client.reset();
+        client.doRequest(0); // Unlimited
+        assertTrue(client.isResponse200());
+        assertTrue(client.isResponseBodyOK());
+        client.reset();
+        client.doRequest(1); // 1 byte - too small should fail
+        assertTrue(client.isResponse500());
+        
+        client.reset();
+        
+        // Edge cases around actual content length
+        client.reset();
+        client.doRequest(6); // Too small should fail
+        assertTrue(client.isResponse500());
+        client.reset();
+        client.doRequest(7); // Just enough should pass
+        assertTrue(client.isResponse200());
+        assertTrue(client.isResponseBodyOK());
+        client.reset();
+        client.doRequest(8); // 1 extra - should pass
+        assertTrue(client.isResponse200());
+        assertTrue(client.isResponseBodyOK());
+        
+        // Much larger
+        client.reset();
+        client.doRequest(8096); // Plenty of space - should pass
+        assertTrue(client.isResponse200());
+        assertTrue(client.isResponseBodyOK());
+    }
+    
+    private static class Bug37794Servlet extends HttpServlet {
+        
+        /**
+         * Only interested in the parameters and values for POST requests.
+         */
+        @Override
+        protected void doPost(HttpServletRequest req, HttpServletResponse resp)
+                throws ServletException, IOException {
+            // Just echo the parameters and values back as plain text
+            resp.setContentType("text/plain");
+            
+            PrintWriter out = resp.getWriter();
+            
+            // Assume one value per attribute
+            Enumeration<String> names = req.getParameterNames();
+            while (names.hasMoreElements()) {
+                String name = names.nextElement();
+                out.println(name + "=" + req.getParameter(name));
+            }
+        }
+    }
+    
+    /**
+     * Bug 37794 test client.
+     */
+    private static class Bug37794Client extends SimpleHttpClient {
+        private Exception doRequest(int postLimit) {
+            Tomcat tomcat = new Tomcat();
+            try {
+                StandardContext root = tomcat.addContext("", TEMP_DIR);
+                Tomcat.addServlet(root, "Bug37794", new Bug37794Servlet());
+                root.addServletMapping("/test", "Bug37794");
+                tomcat.getConnector().setMaxPostSize(postLimit);
+                tomcat.start();
+                
+                // Open connection
+                connect();
+                
+                // Send request in two parts
+                String[] request = new String[2];
+                request[0] =
+                    "POST http://localhost:8080/test HTTP/1.1" + CRLF +
+                    "content-type: application/x-www-form-urlencoded" + CRLF +
+                    "Transfer-Encoding: chunked" + CRLF +
+                    "Connection: close" + CRLF +
+                    CRLF +
+                    "3" + CRLF +
+                    "a=1" + CRLF;
+                request[1] =
+                    "4" + CRLF +
+                    "&b=2" + CRLF +
+                    "0" + CRLF +
+                    CRLF;
+                
+                setRequest(request);
+                processRequest(); // blocks until response has been read
+                
+                // Close the connection
+                disconnect();
+            } catch (Exception e) {
+                return e;
+            } finally {
+                try {
+                    tomcat.stop();
+                } catch (Exception e) {
+                    // Ignore
+                }
+            }
+            return null;
+        }
+
+        public boolean isResponseBodyOK() {
+            if (getResponseBody() == null) {
+                return false;
+            }
+            if (!getResponseBody().contains("a=1")) {
+                return false;
+            }
+            if (!getResponseBody().contains("b=2")) {
+                return false;
+            }
+            return true;
+        }
+        
+    }
+
+    /**
+     * Simple client for unit testing. It isn't robust, it isn't secure and
+     * should not be used as the basis for production code. Its only purpose
+     * is to do the bare minimum for the unit tests. 
+     */
+    private abstract static class SimpleHttpClient {
+        public static final String TEMP_DIR =
+            System.getProperty("java.io.tmpdir");
+        
+        public static final String CRLF = "\r\n";
+
+        public static final String OK_200 = "HTTP/1.1 200";
+        public static final String FAIL_500 = "HTTP/1.1 500";
+        
+        private Socket socket;
+        private Writer writer;
+        private BufferedReader reader;
+        
+        private String[] request;
+        private int requestPause = 1000;
+        
+        private String responseLine;
+        private List<String> responseHeaders = new ArrayList<String>();
+        private String responseBody;
+
+        public void setRequest(String[] theRequest) {
+            request = theRequest;
+        }
+        
+        public void setRequestPause(int theRequestPause) {
+            requestPause = theRequestPause;
+        }
+
+        public String getResponseLine() {
+            return responseLine;
+        }
+
+        public List<String> getResponseHeaders() {
+            return responseHeaders;
+        }
+
+        public String getResponseBody() {
+            return responseBody;
+        }
+
+        public void connect() throws UnknownHostException, IOException {
+            socket = new Socket("localhost", 8080);
+            OutputStream os = socket.getOutputStream();
+            writer = new OutputStreamWriter(os);
+            InputStream is = socket.getInputStream();
+            Reader r = new InputStreamReader(is);
+            reader = new BufferedReader(r);
+        }
+        
+        public void processRequest() throws IOException, InterruptedException {
+            // Send the request
+            boolean first = true;
+            for (String requestPart : request) {
+                if (first) {
+                    first = false;
+                } else {
+                    Thread.sleep(requestPause);
+                }
+                writer.write(requestPart);
+                writer.flush();
+            }
+
+            // Read the response
+            responseLine = readLine();
+            
+            // Put the headers into the map
+            String line = readLine();
+            while (line.length() > 0) {
+                responseHeaders.add(line);
+                line = readLine();
+            }
+            
+            // Read the body, if any
+            StringBuilder builder = new StringBuilder();
+            line = readLine();
+            while (line != null && line.length() > 0) {
+                builder.append(line);
+                line = readLine();
+            }
+            responseBody = builder.toString();
+
+        }
+
+        public String readLine() throws IOException {
+            return reader.readLine();
+        }
+        
+        public void disconnect() throws IOException {
+            writer.close();
+            reader.close();
+            socket.close();
+        }
+        
+        public void reset() {
+            socket = null;
+            writer = null;
+            reader = null;
+            
+            request = null;
+            requestPause = 1000;
+            
+            responseLine = null;
+            responseHeaders = new ArrayList<String>();
+            responseBody = null;
+        }
+        
+        public boolean isResponse200() {
+            return getResponseLine().startsWith(OK_200);
+        }
+        
+        public boolean isResponse500() {
+            return getResponseLine().startsWith(FAIL_500);
+        }
+
+        public abstract boolean isResponseBodyOK();
+    }
+}

Propchange: tomcat/trunk/test/org/apache/catalina/connector/TestRequest.java
------------------------------------------------------------------------------
    svn:eol-style = native

Propchange: tomcat/trunk/test/org/apache/catalina/connector/TestRequest.java
------------------------------------------------------------------------------
    svn:keywords = Date Author Id Revision



---------------------------------------------------------------------
To unsubscribe, e-mail: dev-unsubscr...@tomcat.apache.org
For additional commands, e-mail: dev-h...@tomcat.apache.org

Reply via email to