Testfall für juplo-cachecontrol implementiert
[percentcodec] / cachecontrol / src / test / java / de / halbekunst / juplo / cachecontrol / HttpTestCase.java
diff --git a/cachecontrol/src/test/java/de/halbekunst/juplo/cachecontrol/HttpTestCase.java b/cachecontrol/src/test/java/de/halbekunst/juplo/cachecontrol/HttpTestCase.java
new file mode 100644 (file)
index 0000000..6fe096e
--- /dev/null
@@ -0,0 +1,193 @@
+package de.halbekunst.juplo.cachecontrol;
+
+import com.meterware.httpunit.WebResponse;
+import com.meterware.servletunit.InvocationContext;
+import com.meterware.servletunit.ServletRunner;
+import com.meterware.servletunit.ServletUnitClient;
+import java.io.IOException;
+import java.io.PrintWriter;
+import java.util.Enumeration;
+import java.util.HashMap;
+import java.util.Map;
+import javax.servlet.ServletOutputStream;
+import javax.servlet.http.HttpServletRequest;
+import javax.servlet.http.HttpServletResponse;
+import javax.servlet.http.HttpServletResponseWrapper;
+import org.junit.Before;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+/**
+ *
+ * @author kai
+ */
+public abstract class HttpTestCase {
+  private final static Logger log = LoggerFactory.getLogger(HttpTestCase.class);
+
+  private ServletRunner sr;
+  ServletUnitClient client;
+  int buffer = 2048;
+
+
+  @Before
+  public void init() throws Exception {
+    sr = new ServletRunner(ParameterGuessingTest.class.getResourceAsStream("/web.xml"));
+    client = sr.newClient();
+  }
+
+  protected WebResponse executeRequest(String uri) throws Exception {
+    log.debug("---------- GET: {}", uri);
+    InvocationContext invocation = client.newInvocation(uri);
+    HttpServletRequest request = invocation.getRequest();
+    log.debug("Request - {}: {}", request.getMethod(), request.getProtocol());
+    Enumeration<String> headers = request.getHeaderNames();
+    while (headers.hasMoreElements()) {
+      String header = headers.nextElement();
+      Enumeration<String> values = request.getHeaders(header);
+      while (values.hasMoreElements())
+        log.debug("Request - {}: {}", header, values.nextElement());
+    }
+    log.debug("Invocing service method.");
+
+    /**
+     * We cannot call invocation.service(), because we have to wrap the
+     * response. Therefore this was coppied from InvocationContextImpl.
+     */
+    TestHttpServletResponse wrappedResponse = new TestHttpServletResponse(invocation.getResponse());
+    if (invocation.isFilterActive()) {
+      invocation.getFilter().doFilter(invocation.getRequest(), wrappedResponse, invocation.getFilterChain());
+    }
+    else {
+      invocation.getServlet().service(invocation.getRequest(), wrappedResponse);
+    }
+
+    WebResponse response = client.getResponse(invocation);
+    log.debug("Response - {}: {}", response.getResponseCode(), response.getResponseMessage());
+    log.debug("Response - {}, {} bytes", response.getContentType(), wrappedResponse.getCount());
+    for (String header : response.getHeaderFieldNames()) {
+      for (String value : response.getHeaderFields(header)) {
+        log.debug("Response - {}: {}", header, value);
+      }
+    }
+    return response;
+  }
+
+
+  class TestHttpServletResponse extends HttpServletResponseWrapper {
+
+    private CountingServletOutputStream out;
+    private HttpServletResponse response;
+    private ServletOutputStream stream;
+    private PrintWriter writer;
+    private boolean committed = false;
+
+
+    TestHttpServletResponse(HttpServletResponse response) {
+      super(response);
+      this.response = response;
+    }
+
+
+    public long getCount() {
+      if (out == null)
+        return -1l;
+      else
+        return out.count;
+    }
+
+
+    @Override
+    public void flushBuffer() throws IOException {
+      committed = true;
+      super.flushBuffer();
+    }
+
+    @Override
+    public int getBufferSize() {
+      return buffer;
+    }
+
+    @Override
+    public boolean isCommitted() {
+      return committed;
+    }
+
+    @Override
+    public void reset() {
+      if (committed)
+        throw new IllegalStateException("call to reset() after response has been commited!");
+      if (out != null)
+        out.count = 0;
+      super.reset();
+    }
+
+    @Override
+    public void resetBuffer() {
+      if (committed)
+        throw new IllegalStateException("call to resetBuffer() after response has been commited!");
+      if (out != null)
+        out.count = 0;
+      super.resetBuffer();
+    }
+
+    @Override
+    public void setBufferSize(int size) {
+      if (out != null && out.count > 0)
+        throw new IllegalStateException("call to setBuffer() after content has been written!");
+      buffer = size;
+    }
+
+    @Override
+    public ServletOutputStream getOutputStream() throws IOException {
+
+      if (writer != null)
+        throw new IllegalStateException("ServletOutputStream and PrintWriter cannot be requested both!");
+
+      if (stream == null) {
+        out = new CountingServletOutputStream(response.getOutputStream());
+        stream = out;
+      }
+
+      return stream;
+    }
+
+    @Override
+    public PrintWriter getWriter() throws IOException {
+
+      if (stream != null)
+        throw new IllegalStateException("ServletOutputStream and PrintWriter cannot be requested both!");
+
+      if (writer == null) {
+        out = new CountingServletOutputStream(response.getOutputStream());
+        writer = new PrintWriter(out);
+      }
+
+      return writer;
+    }
+
+
+    class CountingServletOutputStream extends ServletOutputStream {
+
+      private ServletOutputStream out;
+      long count = 0l;
+
+
+      CountingServletOutputStream(ServletOutputStream out) {
+        this.out = out;
+      }
+
+
+      @Override
+      public void write(int i) throws IOException {
+        count++;
+        /** Simulate commit, when count is getting bigger then buffer */
+        if (count == buffer + 1) {
+          log.debug("simulating commit because buffer overflow! buffer: {}, count: {}", buffer, count);
+          committed = true;
+        }
+        out.write(i);
+      }
+    }
+  }
+}
+