diff options
Diffstat (limited to 'core/src/test/java/fi/iki')
22 files changed, 1965 insertions, 707 deletions
diff --git a/core/src/test/java/fi/iki/elonen/HttpChunkedResponseTest.java b/core/src/test/java/fi/iki/elonen/HttpChunkedResponseTest.java index c3fb1f0..8853efa 100644 --- a/core/src/test/java/fi/iki/elonen/HttpChunkedResponseTest.java +++ b/core/src/test/java/fi/iki/elonen/HttpChunkedResponseTest.java @@ -1,46 +1,50 @@ package fi.iki.elonen; +/* + * #%L + * NanoHttpd-Core + * %% + * Copyright (C) 2012 - 2015 nanohttpd + * %% + * Redistribution and use in source and binary forms, with or without modification, + * are permitted provided that the following conditions are met: + * + * 1. Redistributions of source code must retain the above copyright notice, this + * list of conditions and the following disclaimer. + * + * 2. Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * 3. Neither the name of the nanohttpd nor the names of its contributors + * may be used to endorse or promote products derived from this software without + * specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. + * IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, + * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, + * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF + * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE + * OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED + * OF THE POSSIBILITY OF SUCH DAMAGE. + * #L% + */ + +import static fi.iki.elonen.NanoHTTPD.Response.Status.OK; + import java.io.ByteArrayOutputStream; import java.io.IOException; import java.io.PipedInputStream; -import static fi.iki.elonen.NanoHTTPD.Response.Status.OK; - public class HttpChunkedResponseTest extends HttpServerTest { - @org.junit.Test - public void thatChunkedContentIsChunked() throws Exception { - PipedInputStream pipedInputStream = new ChunkedInputStream(new String[]{ - "some", - "thing which is longer than sixteen characters", - "whee!", - "" - }); - String[] expected = { - "HTTP/1.1 200 OK", - "Content-Type: what/ever", - "Date: .*", - "Connection: keep-alive", - "Transfer-Encoding: chunked", - "", - "4", - "some", - "2d", - "thing which is longer than sixteen characters", - "5", - "whee!", - "0", - "" - }; - testServer.response = new NanoHTTPD.Response(OK, "what/ever", pipedInputStream); - testServer.response.setChunkedTransfer(true); - - ByteArrayOutputStream byteArrayOutputStream = invokeServer("GET / HTTP/1.0"); - - assertResponse(byteArrayOutputStream, expected); - } private static class ChunkedInputStream extends PipedInputStream { + int chunk = 0; + String[] chunks; private ChunkedInputStream(String[] chunks) { @@ -48,12 +52,45 @@ public class HttpChunkedResponseTest extends HttpServerTest { } @Override - public synchronized int read(byte[] buffer) throws IOException { + public synchronized int read(byte[] buffer, int off, int len) throws IOException { // Too implementation-linked, but... - for (int i = 0; i < chunks[chunk].length(); ++i) { - buffer[i] = (byte) chunks[chunk].charAt(i); + for (int i = 0; i < this.chunks[this.chunk].length(); ++i) { + buffer[i] = (byte) this.chunks[this.chunk].charAt(i); } - return chunks[chunk++].length(); + return this.chunks[this.chunk++].length(); } } + + @org.junit.Test + public void thatChunkedContentIsChunked() throws Exception { + PipedInputStream pipedInputStream = new ChunkedInputStream(new String[]{ + "some", + "thing which is longer than sixteen characters", + "whee!", + "" + }); + String[] expected = { + "HTTP/1.1 200 OK", + "Content-Type: what/ever", + "Date: .*", + "Connection: keep-alive", + "Transfer-Encoding: chunked", + "", + "4", + "some", + "2d", + "thing which is longer than sixteen characters", + "5", + "whee!", + "0", + "" + }; + this.testServer.response = new NanoHTTPD(0) { + }.newChunkedResponse(OK, "what/ever", pipedInputStream); + this.testServer.response.setChunkedTransfer(true); + + ByteArrayOutputStream byteArrayOutputStream = invokeServer("GET / HTTP/1.1"); + + assertResponse(byteArrayOutputStream, expected); + } } diff --git a/core/src/test/java/fi/iki/elonen/HttpDeleteRequestTest.java b/core/src/test/java/fi/iki/elonen/HttpDeleteRequestTest.java index 517ad29..8ce49e1 100644 --- a/core/src/test/java/fi/iki/elonen/HttpDeleteRequestTest.java +++ b/core/src/test/java/fi/iki/elonen/HttpDeleteRequestTest.java @@ -1,102 +1,132 @@ package fi.iki.elonen; -import org.junit.Test; +/* + * #%L + * NanoHttpd-Core + * %% + * Copyright (C) 2012 - 2015 nanohttpd + * %% + * Redistribution and use in source and binary forms, with or without modification, + * are permitted provided that the following conditions are met: + * + * 1. Redistributions of source code must retain the above copyright notice, this + * list of conditions and the following disclaimer. + * + * 2. Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * 3. Neither the name of the nanohttpd nor the names of its contributors + * may be used to endorse or promote products derived from this software without + * specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. + * IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, + * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, + * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF + * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE + * OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED + * OF THE POSSIBILITY OF SUCH DAMAGE. + * #L% + */ import java.io.ByteArrayOutputStream; import java.io.InputStream; -import java.util.List; -import static junit.framework.Assert.*; +import org.junit.Test; public class HttpDeleteRequestTest extends HttpServerTest { @Test public void testDeleteRequestThatDoesntSendBackResponseBody_EmptyString() throws Exception { - testServer.response = new NanoHTTPD.Response(NanoHTTPD.Response.Status.NO_CONTENT, NanoHTTPD.MIME_HTML, ""); + this.testServer.response = NanoHTTPD.newFixedLengthResponse(NanoHTTPD.Response.Status.NO_CONTENT, NanoHTTPD.MIME_HTML, ""); - ByteArrayOutputStream outputStream = invokeServer("DELETE " + URI + " HTTP/1.1"); + ByteArrayOutputStream outputStream = invokeServer("DELETE " + HttpServerTest.URI + " HTTP/1.1"); String[] expected = { - "HTTP/1.1 204 No Content", - "Content-Type: text/html", - "Date: .*", - "Connection: keep-alive", - "Content-Length: 0", - "" + "HTTP/1.1 204 No Content", + "Content-Type: text/html", + "Date: .*", + "Connection: keep-alive", + "Content-Length: 0", + "" }; assertResponse(outputStream, expected); } @Test - public void testDeleteRequestThatDoesntSendBackResponseBody_NullString() throws Exception { - testServer.response = new NanoHTTPD.Response(NanoHTTPD.Response.Status.NO_CONTENT, NanoHTTPD.MIME_HTML, (String)null); + public void testDeleteRequestThatDoesntSendBackResponseBody_NullInputStream() throws Exception { + this.testServer.response = NanoHTTPD.newChunkedResponse(NanoHTTPD.Response.Status.NO_CONTENT, NanoHTTPD.MIME_HTML, (InputStream) null); - ByteArrayOutputStream outputStream = invokeServer("DELETE " + URI + " HTTP/1.1"); + ByteArrayOutputStream outputStream = invokeServer("DELETE " + HttpServerTest.URI + " HTTP/1.1"); String[] expected = { - "HTTP/1.1 204 No Content", - "Content-Type: text/html", - "Date: .*", - "Connection: keep-alive", - "Content-Length: 0", - "" + "HTTP/1.1 204 No Content", + "Content-Type: text/html", + "Date: .*", + "Connection: keep-alive", + "Content-Length: 0", + "" }; assertResponse(outputStream, expected); } @Test - public void testDeleteRequestThatDoesntSendBackResponseBody_NullInputStream() throws Exception { - testServer.response = new NanoHTTPD.Response(NanoHTTPD.Response.Status.NO_CONTENT, NanoHTTPD.MIME_HTML, (InputStream)null); + public void testDeleteRequestThatDoesntSendBackResponseBody_NullString() throws Exception { + this.testServer.response = NanoHTTPD.newFixedLengthResponse(NanoHTTPD.Response.Status.NO_CONTENT, NanoHTTPD.MIME_HTML, (String) null); - ByteArrayOutputStream outputStream = invokeServer("DELETE " + URI + " HTTP/1.1"); + ByteArrayOutputStream outputStream = invokeServer("DELETE " + HttpServerTest.URI + " HTTP/1.1"); String[] expected = { - "HTTP/1.1 204 No Content", - "Content-Type: text/html", - "Date: .*", - "Connection: keep-alive", - "Content-Length: 0", - "" + "HTTP/1.1 204 No Content", + "Content-Type: text/html", + "Date: .*", + "Connection: keep-alive", + "Content-Length: 0", + "" }; assertResponse(outputStream, expected); } @Test - public void testDeleteRequestThatSendsBackResponseBody_Success() throws Exception { - testServer.response = new NanoHTTPD.Response(NanoHTTPD.Response.Status.OK, "application/xml", "<body />"); + public void testDeleteRequestThatSendsBackResponseBody_Accepted() throws Exception { + this.testServer.response = NanoHTTPD.newFixedLengthResponse(NanoHTTPD.Response.Status.ACCEPTED, "application/xml", "<body />"); - ByteArrayOutputStream outputStream = invokeServer("DELETE " + URI + " HTTP/1.1"); + ByteArrayOutputStream outputStream = invokeServer("DELETE " + HttpServerTest.URI + " HTTP/1.1"); String[] expected = { - "HTTP/1.1 200 OK", - "Content-Type: application/xml", - "Date: .*", - "Connection: keep-alive", - "Content-Length: 8", - "", - "<body />" + "HTTP/1.1 202 Accepted", + "Content-Type: application/xml", + "Date: .*", + "Connection: keep-alive", + "Content-Length: 8", + "", + "<body />" }; assertResponse(outputStream, expected); } @Test - public void testDeleteRequestThatSendsBackResponseBody_Accepted() throws Exception { - testServer.response = new NanoHTTPD.Response(NanoHTTPD.Response.Status.ACCEPTED, "application/xml", "<body />"); + public void testDeleteRequestThatSendsBackResponseBody_Success() throws Exception { + this.testServer.response = NanoHTTPD.newFixedLengthResponse(NanoHTTPD.Response.Status.OK, "application/xml", "<body />"); - ByteArrayOutputStream outputStream = invokeServer("DELETE " + URI + " HTTP/1.1"); + ByteArrayOutputStream outputStream = invokeServer("DELETE " + HttpServerTest.URI + " HTTP/1.1"); String[] expected = { - "HTTP/1.1 202 Accepted", - "Content-Type: application/xml", - "Date: .*", - "Connection: keep-alive", - "Content-Length: 8", - "", - "<body />" + "HTTP/1.1 200 OK", + "Content-Type: application/xml", + "Date: .*", + "Connection: keep-alive", + "Content-Length: 8", + "", + "<body />" }; assertResponse(outputStream, expected); diff --git a/core/src/test/java/fi/iki/elonen/HttpGetRequestTest.java b/core/src/test/java/fi/iki/elonen/HttpGetRequestTest.java index 598e50b..e1a6b8b 100644 --- a/core/src/test/java/fi/iki/elonen/HttpGetRequestTest.java +++ b/core/src/test/java/fi/iki/elonen/HttpGetRequestTest.java @@ -1,171 +1,208 @@ package fi.iki.elonen; -import org.junit.Test; +/* + * #%L + * NanoHttpd-Core + * %% + * Copyright (C) 2012 - 2015 nanohttpd + * %% + * Redistribution and use in source and binary forms, with or without modification, + * are permitted provided that the following conditions are met: + * + * 1. Redistributions of source code must retain the above copyright notice, this + * list of conditions and the following disclaimer. + * + * 2. Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * 3. Neither the name of the nanohttpd nor the names of its contributors + * may be used to endorse or promote products derived from this software without + * specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. + * IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, + * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, + * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF + * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE + * OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED + * OF THE POSSIBILITY OF SUCH DAMAGE. + * #L% + */ + +import static junit.framework.Assert.assertEquals; +import static junit.framework.Assert.assertNotNull; +import static junit.framework.Assert.assertTrue; import java.io.ByteArrayOutputStream; import java.util.List; -import static junit.framework.Assert.*; +import org.junit.Test; public class HttpGetRequestTest extends HttpServerTest { @Test - public void testFullyQualifiedWorkingGetRequest() throws Exception { - ByteArrayOutputStream outputStream = invokeServer("GET " + URI + " HTTP/1.1"); - - String[] expected = { - "HTTP/1.1 200 OK", - "Content-Type: text/html", - "Date: .*", - "Connection: keep-alive", - "Content-Length: 0", - "" - }; - - assertResponse(outputStream, expected); + public void testDecodingFieldWithEmptyValueAndFieldWithMissingValueGiveDifferentResults() { + invokeServer("GET " + HttpServerTest.URI + "?foo&bar= HTTP/1.1"); + assertTrue(this.testServer.decodedParamters.get("foo") instanceof List); + assertEquals(0, this.testServer.decodedParamters.get("foo").size()); + assertTrue(this.testServer.decodedParamters.get("bar") instanceof List); + assertEquals(1, this.testServer.decodedParamters.get("bar").size()); + assertEquals("", this.testServer.decodedParamters.get("bar").get(0)); } @Test - public void testOutputOfServeSentBackToClient() throws Exception { - String responseBody = "Success!"; - testServer.response = new NanoHTTPD.Response(responseBody); - ByteArrayOutputStream outputStream = invokeServer("GET " + URI + " HTTP/1.1"); - - String[] expected = { - "HTTP/1.1 200 OK", - "Content-Type: text/html", - "Date: .*", - "Connection: keep-alive", - "Content-Length: 8", - "", - responseBody - }; + public void testDecodingMixtureOfParameters() { + invokeServer("GET " + HttpServerTest.URI + "?foo=bar&foo=baz&zot&zim= HTTP/1.1"); + assertTrue(this.testServer.decodedParamters.get("foo") instanceof List); + assertEquals(2, this.testServer.decodedParamters.get("foo").size()); + assertEquals("bar", this.testServer.decodedParamters.get("foo").get(0)); + assertEquals("baz", this.testServer.decodedParamters.get("foo").get(1)); + assertTrue(this.testServer.decodedParamters.get("zot") instanceof List); + assertEquals(0, this.testServer.decodedParamters.get("zot").size()); + assertTrue(this.testServer.decodedParamters.get("zim") instanceof List); + assertEquals(1, this.testServer.decodedParamters.get("zim").size()); + assertEquals("", this.testServer.decodedParamters.get("zim").get(0)); + } - assertResponse(outputStream, expected); + @Test + public void testDecodingParametersFromParameterMap() { + invokeServer("GET " + HttpServerTest.URI + "?foo=bar&foo=baz&zot&zim= HTTP/1.1"); + assertEquals(this.testServer.decodedParamters, this.testServer.decodedParamtersFromParameter); } + // -------------------------------------------------------------------------------------------------------- + // // + @Test - public void testEmptyHeadersSuppliedToServeMethodFromSimpleWorkingGetRequest() { - invokeServer("GET " + URI + " HTTP/1.1"); - assertNotNull(testServer.parms); - assertNotNull(testServer.header); - assertNotNull(testServer.files); - assertNotNull(testServer.uri); + public void testDecodingParametersWithSingleValue() { + invokeServer("GET " + HttpServerTest.URI + "?foo=bar&baz=zot HTTP/1.1"); + assertEquals("foo=bar&baz=zot", this.testServer.queryParameterString); + assertTrue(this.testServer.decodedParamters.get("foo") instanceof List); + assertEquals(1, this.testServer.decodedParamters.get("foo").size()); + assertEquals("bar", this.testServer.decodedParamters.get("foo").get(0)); + assertTrue(this.testServer.decodedParamters.get("baz") instanceof List); + assertEquals(1, this.testServer.decodedParamters.get("baz").size()); + assertEquals("zot", this.testServer.decodedParamters.get("baz").get(0)); } @Test - public void testSingleUserAgentHeaderSuppliedToServeMethodFromSimpleWorkingGetRequest() { - String userAgent = "jUnit 4.8.2 Unit Test"; - invokeServer("GET " + URI + " HTTP/1.1\nUser-Agent: " + userAgent + "\n"); - assertEquals(userAgent, testServer.header.get("user-agent")); - assertEquals(NanoHTTPD.Method.GET, testServer.method); - assertEquals(URI, testServer.uri); + public void testDecodingParametersWithSingleValueAndMissingValue() { + invokeServer("GET " + HttpServerTest.URI + "?foo&baz=zot HTTP/1.1"); + assertEquals("foo&baz=zot", this.testServer.queryParameterString); + assertTrue(this.testServer.decodedParamters.get("foo") instanceof List); + assertEquals(0, this.testServer.decodedParamters.get("foo").size()); + assertTrue(this.testServer.decodedParamters.get("baz") instanceof List); + assertEquals(1, this.testServer.decodedParamters.get("baz").size()); + assertEquals("zot", this.testServer.decodedParamters.get("baz").get(0)); } @Test - public void testMultipleHeaderSuppliedToServeMethodFromSimpleWorkingGetRequest() { - String userAgent = "jUnit 4.8.2 Unit Test"; - String accept = "text/html"; - invokeServer("GET " + URI + " HTTP/1.1\nUser-Agent: " + userAgent + "\nAccept: " + accept); - assertEquals(userAgent, testServer.header.get("user-agent")); - assertEquals(accept, testServer.header.get("accept")); + public void testDecodingSingleFieldRepeated() { + invokeServer("GET " + HttpServerTest.URI + "?foo=bar&foo=baz HTTP/1.1"); + assertTrue(this.testServer.decodedParamters.get("foo") instanceof List); + assertEquals(2, this.testServer.decodedParamters.get("foo").size()); + assertEquals("bar", this.testServer.decodedParamters.get("foo").get(0)); + assertEquals("baz", this.testServer.decodedParamters.get("foo").get(1)); } @Test - public void testSingleGetParameter() { - invokeServer("GET " + URI + "?foo=bar HTTP/1.1"); - assertEquals("bar", testServer.parms.get("foo")); + public void testEmptyHeadersSuppliedToServeMethodFromSimpleWorkingGetRequest() { + invokeServer("GET " + HttpServerTest.URI + " HTTP/1.1"); + assertNotNull(this.testServer.parms); + assertNotNull(this.testServer.header); + assertNotNull(this.testServer.files); + assertNotNull(this.testServer.uri); } @Test - public void testSingleGetParameterWithNoValue() { - invokeServer("GET " + URI + "?foo HTTP/1.1"); - assertEquals("", testServer.parms.get("foo")); + public void testFullyQualifiedWorkingGetRequest() throws Exception { + ByteArrayOutputStream outputStream = invokeServer("GET " + HttpServerTest.URI + " HTTP/1.1"); + + String[] expected = { + "HTTP/1.1 200 OK", + "Content-Type: text/html", + "Date: .*", + "Connection: keep-alive", + "Content-Length: 0", + "" + }; + + assertResponse(outputStream, expected); } @Test public void testMultipleGetParameters() { - invokeServer("GET " + URI + "?foo=bar&baz=zot HTTP/1.1"); - assertEquals("bar", testServer.parms.get("foo")); - assertEquals("zot", testServer.parms.get("baz")); + invokeServer("GET " + HttpServerTest.URI + "?foo=bar&baz=zot HTTP/1.1"); + assertEquals("bar", this.testServer.parms.get("foo")); + assertEquals("zot", this.testServer.parms.get("baz")); } @Test public void testMultipleGetParametersWithMissingValue() { - invokeServer("GET " + URI + "?foo=&baz=zot HTTP/1.1"); - assertEquals("", testServer.parms.get("foo")); - assertEquals("zot", testServer.parms.get("baz")); + invokeServer("GET " + HttpServerTest.URI + "?foo=&baz=zot HTTP/1.1"); + assertEquals("", this.testServer.parms.get("foo")); + assertEquals("zot", this.testServer.parms.get("baz")); } @Test public void testMultipleGetParametersWithMissingValueAndRequestHeaders() { - invokeServer("GET " + URI + "?foo=&baz=zot HTTP/1.1\nAccept: text/html"); - assertEquals("", testServer.parms.get("foo")); - assertEquals("zot", testServer.parms.get("baz")); - assertEquals("text/html", testServer.header.get("accept")); + invokeServer("GET " + HttpServerTest.URI + "?foo=&baz=zot HTTP/1.1\nAccept: text/html"); + assertEquals("", this.testServer.parms.get("foo")); + assertEquals("zot", this.testServer.parms.get("baz")); + assertEquals("text/html", this.testServer.header.get("accept")); } @Test - public void testDecodingParametersWithSingleValue() { - invokeServer("GET " + URI + "?foo=bar&baz=zot HTTP/1.1"); - assertEquals("foo=bar&baz=zot", testServer.queryParameterString); - assertTrue(testServer.decodedParamters.get("foo") instanceof List); - assertEquals(1, testServer.decodedParamters.get("foo").size()); - assertEquals("bar", testServer.decodedParamters.get("foo").get(0)); - assertTrue(testServer.decodedParamters.get("baz") instanceof List); - assertEquals(1, testServer.decodedParamters.get("baz").size()); - assertEquals("zot", testServer.decodedParamters.get("baz").get(0)); + public void testMultipleHeaderSuppliedToServeMethodFromSimpleWorkingGetRequest() { + String userAgent = "jUnit 4.8.2 Unit Test"; + String accept = "text/html"; + invokeServer("GET " + HttpServerTest.URI + " HTTP/1.1\nUser-Agent: " + userAgent + "\nAccept: " + accept); + assertEquals(userAgent, this.testServer.header.get("user-agent")); + assertEquals(accept, this.testServer.header.get("accept")); } @Test - public void testDecodingParametersWithSingleValueAndMissingValue() { - invokeServer("GET " + URI + "?foo&baz=zot HTTP/1.1"); - assertEquals("foo&baz=zot", testServer.queryParameterString); - assertTrue(testServer.decodedParamters.get("foo") instanceof List); - assertEquals(0, testServer.decodedParamters.get("foo").size()); - assertTrue(testServer.decodedParamters.get("baz") instanceof List); - assertEquals(1, testServer.decodedParamters.get("baz").size()); - assertEquals("zot", testServer.decodedParamters.get("baz").get(0)); - } + public void testOutputOfServeSentBackToClient() throws Exception { + String responseBody = "Success!"; + this.testServer.response = NanoHTTPD.newFixedLengthResponse(responseBody); + ByteArrayOutputStream outputStream = invokeServer("GET " + HttpServerTest.URI + " HTTP/1.1"); - @Test - public void testDecodingFieldWithEmptyValueAndFieldWithMissingValueGiveDifferentResults() { - invokeServer("GET " + URI + "?foo&bar= HTTP/1.1"); - assertTrue(testServer.decodedParamters.get("foo") instanceof List); - assertEquals(0, testServer.decodedParamters.get("foo").size()); - assertTrue(testServer.decodedParamters.get("bar") instanceof List); - assertEquals(1, testServer.decodedParamters.get("bar").size()); - assertEquals("", testServer.decodedParamters.get("bar").get(0)); + String[] expected = { + "HTTP/1.1 200 OK", + "Content-Type: text/html", + "Date: .*", + "Connection: keep-alive", + "Content-Length: 8", + "", + responseBody + }; + + assertResponse(outputStream, expected); } @Test - public void testDecodingSingleFieldRepeated() { - invokeServer("GET " + URI + "?foo=bar&foo=baz HTTP/1.1"); - assertTrue(testServer.decodedParamters.get("foo") instanceof List); - assertEquals(2, testServer.decodedParamters.get("foo").size()); - assertEquals("bar", testServer.decodedParamters.get("foo").get(0)); - assertEquals("baz", testServer.decodedParamters.get("foo").get(1)); + public void testSingleGetParameter() { + invokeServer("GET " + HttpServerTest.URI + "?foo=bar HTTP/1.1"); + assertEquals("bar", this.testServer.parms.get("foo")); } @Test - public void testDecodingMixtureOfParameters() { - invokeServer("GET " + URI + "?foo=bar&foo=baz&zot&zim= HTTP/1.1"); - assertTrue(testServer.decodedParamters.get("foo") instanceof List); - assertEquals(2, testServer.decodedParamters.get("foo").size()); - assertEquals("bar", testServer.decodedParamters.get("foo").get(0)); - assertEquals("baz", testServer.decodedParamters.get("foo").get(1)); - assertTrue(testServer.decodedParamters.get("zot") instanceof List); - assertEquals(0, testServer.decodedParamters.get("zot").size()); - assertTrue(testServer.decodedParamters.get("zim") instanceof List); - assertEquals(1, testServer.decodedParamters.get("zim").size()); - assertEquals("", testServer.decodedParamters.get("zim").get(0)); + public void testSingleGetParameterWithNoValue() { + invokeServer("GET " + HttpServerTest.URI + "?foo HTTP/1.1"); + assertEquals("", this.testServer.parms.get("foo")); } @Test - public void testDecodingParametersFromParameterMap() { - invokeServer("GET " + URI + "?foo=bar&foo=baz&zot&zim= HTTP/1.1"); - assertEquals(testServer.decodedParamters, testServer.decodedParamtersFromParameter); + public void testSingleUserAgentHeaderSuppliedToServeMethodFromSimpleWorkingGetRequest() { + String userAgent = "jUnit 4.8.2 Unit Test"; + invokeServer("GET " + HttpServerTest.URI + " HTTP/1.1\nUser-Agent: " + userAgent + "\n"); + assertEquals(userAgent, this.testServer.header.get("user-agent")); + assertEquals(NanoHTTPD.Method.GET, this.testServer.method); + assertEquals(HttpServerTest.URI, this.testServer.uri); } - // -------------------------------------------------------------------------------------------------------- // } diff --git a/core/src/test/java/fi/iki/elonen/HttpHeadRequestTest.java b/core/src/test/java/fi/iki/elonen/HttpHeadRequestTest.java index 1c5901f..9b5983e 100644 --- a/core/src/test/java/fi/iki/elonen/HttpHeadRequestTest.java +++ b/core/src/test/java/fi/iki/elonen/HttpHeadRequestTest.java @@ -1,158 +1,196 @@ package fi.iki.elonen; -import org.junit.Test; +/* + * #%L + * NanoHttpd-Core + * %% + * Copyright (C) 2012 - 2015 nanohttpd + * %% + * Redistribution and use in source and binary forms, with or without modification, + * are permitted provided that the following conditions are met: + * + * 1. Redistributions of source code must retain the above copyright notice, this + * list of conditions and the following disclaimer. + * + * 2. Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * 3. Neither the name of the nanohttpd nor the names of its contributors + * may be used to endorse or promote products derived from this software without + * specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. + * IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, + * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, + * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF + * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE + * OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED + * OF THE POSSIBILITY OF SUCH DAMAGE. + * #L% + */ + +import static junit.framework.Assert.assertEquals; +import static junit.framework.Assert.assertNotNull; +import static junit.framework.Assert.assertTrue; import java.io.ByteArrayOutputStream; import java.util.List; -import static junit.framework.Assert.*; +import org.junit.Test; public class HttpHeadRequestTest extends HttpServerTest { + @Override - public void setUp() { + public void setUp() throws Exception { super.setUp(); String responseBody = "Success!"; - testServer.response = new NanoHTTPD.Response(responseBody); + this.testServer.response = NanoHTTPD.newFixedLengthResponse(responseBody); } @Test - public void testHeadRequestDoesntSendBackResponseBody() throws Exception { - ByteArrayOutputStream outputStream = invokeServer("HEAD " + URI + " HTTP/1.1"); - - String[] expected = { - "HTTP/1.1 200 OK", - "Content-Type: text/html", - "Date: .*", - "Connection: keep-alive", - "Content-Length: 8", - "" - }; - - assertResponse(outputStream, expected); + public void testDecodingFieldWithEmptyValueAndFieldWithMissingValueGiveDifferentResults() { + invokeServer("HEAD " + HttpServerTest.URI + "?foo&bar= HTTP/1.1"); + assertTrue(this.testServer.decodedParamters.get("foo") instanceof List); + assertEquals(0, this.testServer.decodedParamters.get("foo").size()); + assertTrue(this.testServer.decodedParamters.get("bar") instanceof List); + assertEquals(1, this.testServer.decodedParamters.get("bar").size()); + assertEquals("", this.testServer.decodedParamters.get("bar").get(0)); } @Test - public void testEmptyHeadersSuppliedToServeMethodFromSimpleWorkingGetRequest() { - invokeServer("HEAD " + URI + " HTTP/1.1"); - assertNotNull(testServer.parms); - assertNotNull(testServer.header); - assertNotNull(testServer.files); - assertNotNull(testServer.uri); + public void testDecodingMixtureOfParameters() { + invokeServer("HEAD " + HttpServerTest.URI + "?foo=bar&foo=baz&zot&zim= HTTP/1.1"); + assertTrue(this.testServer.decodedParamters.get("foo") instanceof List); + assertEquals(2, this.testServer.decodedParamters.get("foo").size()); + assertEquals("bar", this.testServer.decodedParamters.get("foo").get(0)); + assertEquals("baz", this.testServer.decodedParamters.get("foo").get(1)); + assertTrue(this.testServer.decodedParamters.get("zot") instanceof List); + assertEquals(0, this.testServer.decodedParamters.get("zot").size()); + assertTrue(this.testServer.decodedParamters.get("zim") instanceof List); + assertEquals(1, this.testServer.decodedParamters.get("zim").size()); + assertEquals("", this.testServer.decodedParamters.get("zim").get(0)); } @Test - public void testSingleUserAgentHeaderSuppliedToServeMethodFromSimpleWorkingGetRequest() { - String userAgent = "jUnit 4.8.2 Unit Test"; - invokeServer("HEAD " + URI + " HTTP/1.1\nUser-Agent: " + userAgent + "\n"); - assertEquals(userAgent, testServer.header.get("user-agent")); - assertEquals(NanoHTTPD.Method.HEAD, testServer.method); - assertEquals(URI, testServer.uri); + public void testDecodingParametersFromParameterMap() { + invokeServer("HEAD " + HttpServerTest.URI + "?foo=bar&foo=baz&zot&zim= HTTP/1.1"); + assertEquals(this.testServer.decodedParamters, this.testServer.decodedParamtersFromParameter); } + // -------------------------------------------------------------------------------------------------------- + // // + @Test - public void testMultipleHeaderSuppliedToServeMethodFromSimpleWorkingGetRequest() { - String userAgent = "jUnit 4.8.2 Unit Test"; - String accept = "text/html"; - invokeServer("HEAD " + URI + " HTTP/1.1\nUser-Agent: " + userAgent + "\nAccept: " + accept); - assertEquals(userAgent, testServer.header.get("user-agent")); - assertEquals(accept, testServer.header.get("accept")); + public void testDecodingParametersWithSingleValue() { + invokeServer("HEAD " + HttpServerTest.URI + "?foo=bar&baz=zot HTTP/1.1"); + assertEquals("foo=bar&baz=zot", this.testServer.queryParameterString); + assertTrue(this.testServer.decodedParamters.get("foo") instanceof List); + assertEquals(1, this.testServer.decodedParamters.get("foo").size()); + assertEquals("bar", this.testServer.decodedParamters.get("foo").get(0)); + assertTrue(this.testServer.decodedParamters.get("baz") instanceof List); + assertEquals(1, this.testServer.decodedParamters.get("baz").size()); + assertEquals("zot", this.testServer.decodedParamters.get("baz").get(0)); } @Test - public void testSingleGetParameter() { - invokeServer("HEAD " + URI + "?foo=bar HTTP/1.1"); - assertEquals("bar", testServer.parms.get("foo")); + public void testDecodingParametersWithSingleValueAndMissingValue() { + invokeServer("HEAD " + HttpServerTest.URI + "?foo&baz=zot HTTP/1.1"); + assertEquals("foo&baz=zot", this.testServer.queryParameterString); + assertTrue(this.testServer.decodedParamters.get("foo") instanceof List); + assertEquals(0, this.testServer.decodedParamters.get("foo").size()); + assertTrue(this.testServer.decodedParamters.get("baz") instanceof List); + assertEquals(1, this.testServer.decodedParamters.get("baz").size()); + assertEquals("zot", this.testServer.decodedParamters.get("baz").get(0)); } @Test - public void testSingleGetParameterWithNoValue() { - invokeServer("HEAD " + URI + "?foo HTTP/1.1"); - assertEquals("", testServer.parms.get("foo")); + public void testDecodingSingleFieldRepeated() { + invokeServer("HEAD " + HttpServerTest.URI + "?foo=bar&foo=baz HTTP/1.1"); + assertTrue(this.testServer.decodedParamters.get("foo") instanceof List); + assertEquals(2, this.testServer.decodedParamters.get("foo").size()); + assertEquals("bar", this.testServer.decodedParamters.get("foo").get(0)); + assertEquals("baz", this.testServer.decodedParamters.get("foo").get(1)); } @Test - public void testMultipleGetParameters() { - invokeServer("HEAD " + URI + "?foo=bar&baz=zot HTTP/1.1"); - assertEquals("bar", testServer.parms.get("foo")); - assertEquals("zot", testServer.parms.get("baz")); + public void testEmptyHeadersSuppliedToServeMethodFromSimpleWorkingGetRequest() { + invokeServer("HEAD " + HttpServerTest.URI + " HTTP/1.1"); + assertNotNull(this.testServer.parms); + assertNotNull(this.testServer.header); + assertNotNull(this.testServer.files); + assertNotNull(this.testServer.uri); } @Test - public void testMultipleGetParametersWithMissingValue() { - invokeServer("HEAD " + URI + "?foo=&baz=zot HTTP/1.1"); - assertEquals("", testServer.parms.get("foo")); - assertEquals("zot", testServer.parms.get("baz")); + public void testHeadRequestDoesntSendBackResponseBody() throws Exception { + ByteArrayOutputStream outputStream = invokeServer("HEAD " + HttpServerTest.URI + " HTTP/1.1"); + + String[] expected = { + "HTTP/1.1 200 OK", + "Content-Type: text/html", + "Date: .*", + "Connection: keep-alive", + "Content-Length: 8", + "" + }; + + assertResponse(outputStream, expected); } @Test - public void testMultipleGetParametersWithMissingValueAndRequestHeaders() { - invokeServer("HEAD " + URI + "?foo=&baz=zot HTTP/1.1\nAccept: text/html"); - assertEquals("", testServer.parms.get("foo")); - assertEquals("zot", testServer.parms.get("baz")); - assertEquals("text/html", testServer.header.get("accept")); + public void testMultipleGetParameters() { + invokeServer("HEAD " + HttpServerTest.URI + "?foo=bar&baz=zot HTTP/1.1"); + assertEquals("bar", this.testServer.parms.get("foo")); + assertEquals("zot", this.testServer.parms.get("baz")); } @Test - public void testDecodingParametersWithSingleValue() { - invokeServer("HEAD " + URI + "?foo=bar&baz=zot HTTP/1.1"); - assertEquals("foo=bar&baz=zot", testServer.queryParameterString); - assertTrue(testServer.decodedParamters.get("foo") instanceof List); - assertEquals(1, testServer.decodedParamters.get("foo").size()); - assertEquals("bar", testServer.decodedParamters.get("foo").get(0)); - assertTrue(testServer.decodedParamters.get("baz") instanceof List); - assertEquals(1, testServer.decodedParamters.get("baz").size()); - assertEquals("zot", testServer.decodedParamters.get("baz").get(0)); + public void testMultipleGetParametersWithMissingValue() { + invokeServer("HEAD " + HttpServerTest.URI + "?foo=&baz=zot HTTP/1.1"); + assertEquals("", this.testServer.parms.get("foo")); + assertEquals("zot", this.testServer.parms.get("baz")); } @Test - public void testDecodingParametersWithSingleValueAndMissingValue() { - invokeServer("HEAD " + URI + "?foo&baz=zot HTTP/1.1"); - assertEquals("foo&baz=zot", testServer.queryParameterString); - assertTrue(testServer.decodedParamters.get("foo") instanceof List); - assertEquals(0, testServer.decodedParamters.get("foo").size()); - assertTrue(testServer.decodedParamters.get("baz") instanceof List); - assertEquals(1, testServer.decodedParamters.get("baz").size()); - assertEquals("zot", testServer.decodedParamters.get("baz").get(0)); + public void testMultipleGetParametersWithMissingValueAndRequestHeaders() { + invokeServer("HEAD " + HttpServerTest.URI + "?foo=&baz=zot HTTP/1.1\nAccept: text/html"); + assertEquals("", this.testServer.parms.get("foo")); + assertEquals("zot", this.testServer.parms.get("baz")); + assertEquals("text/html", this.testServer.header.get("accept")); } @Test - public void testDecodingFieldWithEmptyValueAndFieldWithMissingValueGiveDifferentResults() { - invokeServer("HEAD " + URI + "?foo&bar= HTTP/1.1"); - assertTrue(testServer.decodedParamters.get("foo") instanceof List); - assertEquals(0, testServer.decodedParamters.get("foo").size()); - assertTrue(testServer.decodedParamters.get("bar") instanceof List); - assertEquals(1, testServer.decodedParamters.get("bar").size()); - assertEquals("", testServer.decodedParamters.get("bar").get(0)); + public void testMultipleHeaderSuppliedToServeMethodFromSimpleWorkingGetRequest() { + String userAgent = "jUnit 4.8.2 Unit Test"; + String accept = "text/html"; + invokeServer("HEAD " + HttpServerTest.URI + " HTTP/1.1\nUser-Agent: " + userAgent + "\nAccept: " + accept); + assertEquals(userAgent, this.testServer.header.get("user-agent")); + assertEquals(accept, this.testServer.header.get("accept")); } @Test - public void testDecodingSingleFieldRepeated() { - invokeServer("HEAD " + URI + "?foo=bar&foo=baz HTTP/1.1"); - assertTrue(testServer.decodedParamters.get("foo") instanceof List); - assertEquals(2, testServer.decodedParamters.get("foo").size()); - assertEquals("bar", testServer.decodedParamters.get("foo").get(0)); - assertEquals("baz", testServer.decodedParamters.get("foo").get(1)); + public void testSingleGetParameter() { + invokeServer("HEAD " + HttpServerTest.URI + "?foo=bar HTTP/1.1"); + assertEquals("bar", this.testServer.parms.get("foo")); } @Test - public void testDecodingMixtureOfParameters() { - invokeServer("HEAD " + URI + "?foo=bar&foo=baz&zot&zim= HTTP/1.1"); - assertTrue(testServer.decodedParamters.get("foo") instanceof List); - assertEquals(2, testServer.decodedParamters.get("foo").size()); - assertEquals("bar", testServer.decodedParamters.get("foo").get(0)); - assertEquals("baz", testServer.decodedParamters.get("foo").get(1)); - assertTrue(testServer.decodedParamters.get("zot") instanceof List); - assertEquals(0, testServer.decodedParamters.get("zot").size()); - assertTrue(testServer.decodedParamters.get("zim") instanceof List); - assertEquals(1, testServer.decodedParamters.get("zim").size()); - assertEquals("", testServer.decodedParamters.get("zim").get(0)); + public void testSingleGetParameterWithNoValue() { + invokeServer("HEAD " + HttpServerTest.URI + "?foo HTTP/1.1"); + assertEquals("", this.testServer.parms.get("foo")); } @Test - public void testDecodingParametersFromParameterMap() { - invokeServer("HEAD " + URI + "?foo=bar&foo=baz&zot&zim= HTTP/1.1"); - assertEquals(testServer.decodedParamters, testServer.decodedParamtersFromParameter); + public void testSingleUserAgentHeaderSuppliedToServeMethodFromSimpleWorkingGetRequest() { + String userAgent = "jUnit 4.8.2 Unit Test"; + invokeServer("HEAD " + HttpServerTest.URI + " HTTP/1.1\nUser-Agent: " + userAgent + "\n"); + assertEquals(userAgent, this.testServer.header.get("user-agent")); + assertEquals(NanoHTTPD.Method.HEAD, this.testServer.method); + assertEquals(HttpServerTest.URI, this.testServer.uri); } - // -------------------------------------------------------------------------------------------------------- // } diff --git a/core/src/test/java/fi/iki/elonen/HttpKeepAliveTest.java b/core/src/test/java/fi/iki/elonen/HttpKeepAliveTest.java index f349ee5..e168814 100644 --- a/core/src/test/java/fi/iki/elonen/HttpKeepAliveTest.java +++ b/core/src/test/java/fi/iki/elonen/HttpKeepAliveTest.java @@ -1,5 +1,38 @@ package fi.iki.elonen; +/* + * #%L + * NanoHttpd-Core + * %% + * Copyright (C) 2012 - 2015 nanohttpd + * %% + * Redistribution and use in source and binary forms, with or without modification, + * are permitted provided that the following conditions are met: + * + * 1. Redistributions of source code must retain the above copyright notice, this + * list of conditions and the following disclaimer. + * + * 2. Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * 3. Neither the name of the nanohttpd nor the names of its contributors + * may be used to endorse or promote products derived from this software without + * specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. + * IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, + * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, + * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF + * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE + * OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED + * OF THE POSSIBILITY OF SUCH DAMAGE. + * #L% + */ + import static junit.framework.Assert.fail; import java.io.ByteArrayOutputStream; @@ -10,68 +43,96 @@ import org.junit.Test; public class HttpKeepAliveTest extends HttpServerTest { + private Throwable error = null; + @Test public void testManyGetRequests() throws Exception { - String request = "GET " + URI + " HTTP/1.1\r\n\r\n"; + String request = "GET " + HttpServerTest.URI + " HTTP/1.1\r\n\r\n"; String[] expected = { - "HTTP/1.1 200 OK", - "Content-Type: text/html", - "Date: .*", - "Connection: keep-alive", - "Content-Length: 0", - "" + "HTTP/1.1 200 OK", + "Content-Type: text/html", + "Date: .*", + "Connection: keep-alive", + "Content-Length: 0", + "" }; testManyRequests(request, expected); } - + @Test public void testManyPutRequests() throws Exception { String data = "BodyData 1\nLine 2"; - String request = "PUT " + URI + " HTTP/1.1\r\nContent-Length: " + data.length() + "\r\n\r\n" + data; + String request = "PUT " + HttpServerTest.URI + " HTTP/1.1\r\nContent-Length: " + data.length() + "\r\n\r\n" + data; String[] expected = { - "HTTP/1.1 200 OK", - "Content-Type: text/html", - "Date: .*", - "Connection: keep-alive", - "Content-Length: 0", - "" + "HTTP/1.1 200 OK", + "Content-Type: text/html", + "Date: .*", + "Connection: keep-alive", + "Content-Length: 0", + "" }; testManyRequests(request, expected); } - private Throwable error = null; - /** - * Issue the given request many times to check whether an error occurs. - * For this test, a small stack size is used, since a stack overflow is among the possible errors. - * @param request The request to issue - * @param expected The expected response + * Issue the given request many times to check whether an error occurs. For + * this test, a small stack size is used, since a stack overflow is among + * the possible errors. + * + * @param request + * The request to issue + * @param expected + * The expected response */ public void testManyRequests(final String request, final String[] expected) throws Exception { Runnable r = new Runnable() { + + @Override public void run() { try { PipedOutputStream requestStream = new PipedOutputStream(); PipedInputStream inputStream = new PipedInputStream(requestStream); ByteArrayOutputStream outputStream = new ByteArrayOutputStream(); - NanoHTTPD.HTTPSession session = testServer.createSession(new TestTempFileManager(), inputStream, outputStream); - for (int i = 0; i < 2048; i++) { - requestStream.write(request.getBytes()); + NanoHTTPD.DefaultTempFileManager tempFileManager = new NanoHTTPD.DefaultTempFileManager(); + try { + NanoHTTPD.HTTPSession session = HttpKeepAliveTest.this.testServer.createSession(tempFileManager, inputStream, outputStream); + for (int i = 0; i < 2048; i++) { + requestStream.write(request.getBytes()); + requestStream.flush(); + outputStream.reset(); + session.execute(); + assertResponse(outputStream, expected); + } + + // Finally, try "Connection: Close" + String closeReq = request.replaceAll("HTTP/1.1", "HTTP/1.1\r\nConnection: Close"); + expected[3] = "Connection: close"; + requestStream.write(closeReq.getBytes()); + outputStream.reset(); requestStream.flush(); - session.execute(); + // Server should now close the socket by throwing a + // SocketException: + try { + session.execute(); + } catch (java.net.SocketException se) { + junit.framework.Assert.assertEquals(se.getMessage(), "NanoHttpd Shutdown"); + } assertResponse(outputStream, expected); + + } finally { + tempFileManager.clear(); } } catch (Throwable t) { - error = t; + HttpKeepAliveTest.this.error = t; } } }; Thread t = new Thread(null, r, "Request Thread", 1 << 17); t.start(); t.join(); - if (error != null) { - fail(""+error); - error.printStackTrace(); + if (this.error != null) { + fail("" + this.error); + this.error.printStackTrace(); } } } diff --git a/core/src/test/java/fi/iki/elonen/HttpParsingTest.java b/core/src/test/java/fi/iki/elonen/HttpParsingTest.java index 9705c5b..1f40f63 100644 --- a/core/src/test/java/fi/iki/elonen/HttpParsingTest.java +++ b/core/src/test/java/fi/iki/elonen/HttpParsingTest.java @@ -1,32 +1,63 @@ package fi.iki.elonen; -import org.junit.Test; - -import java.net.URLDecoder; -import java.net.URLEncoder; +/* + * #%L + * NanoHttpd-Core + * %% + * Copyright (C) 2012 - 2015 nanohttpd + * %% + * Redistribution and use in source and binary forms, with or without modification, + * are permitted provided that the following conditions are met: + * + * 1. Redistributions of source code must retain the above copyright notice, this + * list of conditions and the following disclaimer. + * + * 2. Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * 3. Neither the name of the nanohttpd nor the names of its contributors + * may be used to endorse or promote products derived from this software without + * specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. + * IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, + * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, + * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF + * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE + * OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED + * OF THE POSSIBILITY OF SUCH DAMAGE. + * #L% + */ import static junit.framework.Assert.assertEquals; +import org.junit.Test; + public class HttpParsingTest extends HttpServerTest { + + @Test + public void testMultibyteCharacterSupport() throws Exception { + String expected = "Chinese \u738b Letters"; + String input = "Chinese+%e7%8e%8b+Letters"; + assertEquals(expected, this.testServer.decodePercent(input)); + } + @Test public void testNormalCharacters() throws Exception { for (int i = 0x20; i < 0x80; i++) { String hex = Integer.toHexString(i); String input = "%" + hex; char expected = (char) i; - assertEquals("" + expected, testServer.decodePercent(input)); + assertEquals("" + expected, this.testServer.decodePercent(input)); } } @Test - public void testMultibyteCharacterSupport() throws Exception { - String expected = "Chinese \u738b Letters"; - String input = "Chinese+%e7%8e%8b+Letters"; - assertEquals(expected, testServer.decodePercent(input)); - } - - @Test public void testPlusInQueryParams() throws Exception { - assertEquals("foo bar", testServer.decodePercent("foo+bar")); + assertEquals("foo bar", this.testServer.decodePercent("foo+bar")); } } diff --git a/core/src/test/java/fi/iki/elonen/HttpPostRequestTest.java b/core/src/test/java/fi/iki/elonen/HttpPostRequestTest.java index 3cb37e0..db82e1c 100644 --- a/core/src/test/java/fi/iki/elonen/HttpPostRequestTest.java +++ b/core/src/test/java/fi/iki/elonen/HttpPostRequestTest.java @@ -1,157 +1,184 @@ package fi.iki.elonen; -import org.junit.Test; +/* + * #%L + * NanoHttpd-Core + * %% + * Copyright (C) 2012 - 2015 nanohttpd + * %% + * Redistribution and use in source and binary forms, with or without modification, + * are permitted provided that the following conditions are met: + * + * 1. Redistributions of source code must retain the above copyright notice, this + * list of conditions and the following disclaimer. + * + * 2. Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * 3. Neither the name of the nanohttpd nor the names of its contributors + * may be used to endorse or promote products derived from this software without + * specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. + * IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, + * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, + * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF + * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE + * OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED + * OF THE POSSIBILITY OF SUCH DAMAGE. + * #L% + */ + +import static junit.framework.Assert.assertEquals; import java.io.BufferedReader; import java.io.FileReader; import java.util.ArrayList; -import java.util.Arrays; import java.util.List; import java.util.UUID; -import static junit.framework.Assert.assertEquals; +import org.junit.Test; public class HttpPostRequestTest extends HttpServerTest { public static final String CONTENT_LENGTH = "Content-Length: "; + public static final String FIELD = "caption"; + public static final String VALUE = "Summer vacation"; + public static final String FIELD2 = "location"; + public static final String VALUE2 = "Grand Canyon"; + public static final String POST_RAW_CONTENT_FILE_ENTRY = "postData"; + public static final String VALUE_TEST_SIMPLE_RAW_DATA_WITH_AMPHASIS = "Test raw data & Result value"; - @Test - public void testSimpleRawPostData() throws Exception { - String header = "POST " + URI + " HTTP/1.1\n"; - String content = VALUE_TEST_SIMPLE_RAW_DATA_WITH_AMPHASIS + "\n"; + /** + * contains common preparation steps for testing POST with Multipart Form + * + * @param fileName + * Name of file to be uploaded + * @param fileContent + * Content of file to be uploaded + * @return input String with POST request complete information including + * header, length and content + */ + private String preparePostWithMultipartForm(String fileName, String fileContent) { + String divider = UUID.randomUUID().toString(); + String header = "POST " + HttpServerTest.URI + " HTTP/1.1\nContent-Type: " + "multipart/form-data, boundary=" + divider + "\r\n"; + String content = + "--" + divider + "\r\n" + "Content-Disposition: form-data; name=\"" + HttpPostRequestTest.FIELD + "\"; filename=\"" + fileName + "\"\r\n" + + "Content-Type: image/jpeg\r\n" + "\r\n" + fileContent + "\r\n" + "--" + divider + "--\r\n"; int size = content.length() + header.length(); int contentLengthHeaderValueSize = String.valueOf(size).length(); - int contentLength = size + contentLengthHeaderValueSize + CONTENT_LENGTH.length(); - String input = header + CONTENT_LENGTH + (contentLength+4) + "\r\n\r\n" + content; + int contentLength = size + contentLengthHeaderValueSize + HttpPostRequestTest.CONTENT_LENGTH.length(); + String input = header + HttpPostRequestTest.CONTENT_LENGTH + (contentLength + 5) + "\r\n\r\n" + content; + + return input; + } + + @Test + public void testPostWithMultipartFormUpload() throws Exception { + String filename = "GrandCanyon.txt"; + String fileContent = HttpPostRequestTest.VALUE; + String input = preparePostWithMultipartForm(filename, fileContent); + invokeServer(input); - assertEquals(0, testServer.parms.size()); - assertEquals(1, testServer.files.size()); - assertEquals(VALUE_TEST_SIMPLE_RAW_DATA_WITH_AMPHASIS, testServer.files.get(POST_RAW_CONTENT_FILE_ENTRY)); + + assertEquals(1, this.testServer.parms.size()); + BufferedReader reader = new BufferedReader(new FileReader(this.testServer.files.get(HttpPostRequestTest.FIELD))); + List<String> lines = readLinesFromFile(reader); + assertLinesOfText(new String[]{ + fileContent + }, lines); } @Test - public void testSimplePostWithSingleMultipartFormField() throws Exception { - String divider = UUID.randomUUID().toString(); - String header = "POST " + URI + " HTTP/1.1\nContent-Type: " + - "multipart/form-data; boundary=" + divider + "\n"; - String content = "--" + divider + "\n" + - "Content-Disposition: form-data; name=\""+FIELD+"\"\n" + - "\n" + - VALUE +"\n" + - "--" + divider + "--\n"; - int size = content.length() + header.length(); - int contentLengthHeaderValueSize = String.valueOf(size).length(); - int contentLength = size + contentLengthHeaderValueSize + CONTENT_LENGTH.length(); - String input = header + CONTENT_LENGTH + (contentLength+4) + "\r\n\r\n" + content; + public void testPostWithMultipartFormUploadFilenameHasSpaces() throws Exception { + String fileNameWithSpace = "Grand Canyon.txt"; + String fileContent = HttpPostRequestTest.VALUE; + String input = preparePostWithMultipartForm(fileNameWithSpace, fileContent); + invokeServer(input); - assertEquals(1, testServer.parms.size()); - assertEquals(VALUE, testServer.parms.get(FIELD)); + String fileNameAfter = new ArrayList<String>(this.testServer.parms.values()).get(0); + + assertEquals(fileNameWithSpace, fileNameAfter); } @Test public void testPostWithMultipleMultipartFormFields() throws Exception { String divider = UUID.randomUUID().toString(); - String header = "POST " + URI + " HTTP/1.1\nContent-Type: " + - "multipart/form-data; boundary=" + divider + "\n"; - String content = "--" + divider + "\n" + - "Content-Disposition: form-data; name=\""+FIELD+"\"\n" + - "\n" + - VALUE +"\n" +"--" + divider + "\n" + - "Content-Disposition: form-data; name=\""+FIELD2+"\"\n" + - "\n" + - VALUE2 +"\n" + - "--" + divider + "--\n"; + String header = "POST " + HttpServerTest.URI + " HTTP/1.1\nContent-Type: " + "multipart/form-data; boundary=" + divider + "\n"; + String content = + "--" + divider + "\r\n" + "Content-Disposition: form-data; name=\"" + HttpPostRequestTest.FIELD + "\"\r\n" + "\r\n" + HttpPostRequestTest.VALUE + "\r\n" + + "--" + divider + "\r\n" + "Content-Disposition: form-data; name=\"" + HttpPostRequestTest.FIELD2 + "\"\r\n" + "\r\n" + HttpPostRequestTest.VALUE2 + + "\r\n" + "--" + divider + "--\r\n"; int size = content.length() + header.length(); int contentLengthHeaderValueSize = String.valueOf(size).length(); - int contentLength = size + contentLengthHeaderValueSize + CONTENT_LENGTH.length(); - String input = header + CONTENT_LENGTH + (contentLength+4) + "\r\n\r\n" + content; + int contentLength = size + contentLengthHeaderValueSize + HttpPostRequestTest.CONTENT_LENGTH.length(); + String input = header + HttpPostRequestTest.CONTENT_LENGTH + (contentLength + 4) + "\r\n\r\n" + content; invokeServer(input); - assertEquals(2, testServer.parms.size()); - assertEquals(VALUE, testServer.parms.get(FIELD)); - assertEquals(VALUE2, testServer.parms.get(FIELD2)); + assertEquals(2, this.testServer.parms.size()); + assertEquals(HttpPostRequestTest.VALUE, this.testServer.parms.get(HttpPostRequestTest.FIELD)); + assertEquals(HttpPostRequestTest.VALUE2, this.testServer.parms.get(HttpPostRequestTest.FIELD2)); } @Test public void testPostWithMultipleMultipartFormFieldsWhereContentTypeWasSeparatedByComma() throws Exception { String divider = UUID.randomUUID().toString(); - String header = "POST " + URI + " HTTP/1.1\nContent-Type: " + - "multipart/form-data, boundary=" + divider + "\n"; - String content = "--" + divider + "\n" + - "Content-Disposition: form-data; name=\""+FIELD+"\"\n" + - "\n" + - VALUE +"\n" +"--" + divider + "\n" + - "Content-Disposition: form-data; name=\""+FIELD2+"\"\n" + - "\n" + - VALUE2 +"\n" + - "--" + divider + "--\n"; + String header = "POST " + HttpServerTest.URI + " HTTP/1.1\nContent-Type: " + "multipart/form-data, boundary=" + divider + "\r\n"; + String content = + "--" + divider + "\r\n" + "Content-Disposition: form-data; name=\"" + HttpPostRequestTest.FIELD + "\"\r\n" + "\r\n" + HttpPostRequestTest.VALUE + "\r\n" + + "--" + divider + "\r\n" + "Content-Disposition: form-data; name=\"" + HttpPostRequestTest.FIELD2 + "\"\r\n" + "\r\n" + HttpPostRequestTest.VALUE2 + + "\r\n" + "--" + divider + "--\r\n"; int size = content.length() + header.length(); int contentLengthHeaderValueSize = String.valueOf(size).length(); - int contentLength = size + contentLengthHeaderValueSize + CONTENT_LENGTH.length(); - String input = header + CONTENT_LENGTH + (contentLength+4) + "\r\n\r\n" + content; + int contentLength = size + contentLengthHeaderValueSize + HttpPostRequestTest.CONTENT_LENGTH.length(); + String input = header + HttpPostRequestTest.CONTENT_LENGTH + (contentLength + 4) + "\r\n\r\n" + content; invokeServer(input); - assertEquals(2, testServer.parms.size()); - assertEquals(VALUE, testServer.parms.get(FIELD)); - assertEquals(VALUE2, testServer.parms.get(FIELD2)); + assertEquals(2, this.testServer.parms.size()); + assertEquals(HttpPostRequestTest.VALUE, this.testServer.parms.get(HttpPostRequestTest.FIELD)); + assertEquals(HttpPostRequestTest.VALUE2, this.testServer.parms.get(HttpPostRequestTest.FIELD2)); } - + @Test - public void testPostWithMultipartFormUpload() throws Exception { - String filename = "GrandCanyon.txt"; - String fileContent = VALUE; - String input = preparePostWithMultipartForm(filename, fileContent); - + public void testSimplePostWithSingleMultipartFormField() throws Exception { + String divider = UUID.randomUUID().toString(); + String header = "POST " + HttpServerTest.URI + " HTTP/1.1\nContent-Type: " + "multipart/form-data; boundary=" + divider + "\r\n"; + String content = + "--" + divider + "\r\n" + "Content-Disposition: form-data; name=\"" + HttpPostRequestTest.FIELD + "\"\r\n" + "\r\n" + HttpPostRequestTest.VALUE + "\r\n" + + "--" + divider + "--\r\n"; + int size = content.length() + header.length(); + int contentLengthHeaderValueSize = String.valueOf(size).length(); + int contentLength = size + contentLengthHeaderValueSize + HttpPostRequestTest.CONTENT_LENGTH.length(); + String input = header + HttpPostRequestTest.CONTENT_LENGTH + (contentLength + 4) + "\r\n\r\n" + content; invokeServer(input); - - assertEquals(1, testServer.parms.size()); - BufferedReader reader = new BufferedReader(new FileReader(testServer.files.get(FIELD))); - List<String> lines = readLinesFromFile(reader); - assertLinesOfText(new String[]{fileContent}, lines); + + assertEquals(1, this.testServer.parms.size()); + assertEquals(HttpPostRequestTest.VALUE, this.testServer.parms.get(HttpPostRequestTest.FIELD)); } - + @Test - public void testPostWithMultipartFormUploadFilenameHasSpaces() throws Exception { - String fileNameWithSpace = "Grand Canyon.txt"; - String fileContent = VALUE; - String input = preparePostWithMultipartForm(fileNameWithSpace, fileContent); - - invokeServer(input); - - String fileNameAfter = new ArrayList<String>(testServer.parms.values()).get(0); - - assertEquals(fileNameWithSpace, fileNameAfter); - } - - /** - * contains common preparation steps for testing POST with Multipart Form - * @param fileName Name of file to be uploaded - * @param fileContent Content of file to be uploaded - * @return input String with POST request complete information including header, length and content - */ - private String preparePostWithMultipartForm(String fileName, String fileContent) { - String divider = UUID.randomUUID().toString(); - String header = "POST " + URI + " HTTP/1.1\nContent-Type: " + - "multipart/form-data, boundary=" + divider + "\n"; - String content = "--" + divider + "\n" + - "Content-Disposition: form-data; name=\""+FIELD+"\"; filename=\""+fileName+"\"\n" + - "Content-Type: image/jpeg\r\n"+ - "\r\n" + - fileContent +"\r\n" + - "--" + divider + "--\n"; + public void testSimpleRawPostData() throws Exception { + String header = "POST " + HttpServerTest.URI + " HTTP/1.1\n"; + String content = HttpPostRequestTest.VALUE_TEST_SIMPLE_RAW_DATA_WITH_AMPHASIS + "\r\n"; int size = content.length() + header.length(); int contentLengthHeaderValueSize = String.valueOf(size).length(); - int contentLength = size + contentLengthHeaderValueSize + CONTENT_LENGTH.length(); - String input = header + CONTENT_LENGTH + (contentLength+5) + "\r\n\r\n" + content; - - return input; + int contentLength = size + contentLengthHeaderValueSize + HttpPostRequestTest.CONTENT_LENGTH.length(); + String input = header + HttpPostRequestTest.CONTENT_LENGTH + (contentLength + 4) + "\r\n\r\n" + content; + invokeServer(input); + assertEquals(0, this.testServer.parms.size()); + assertEquals(1, this.testServer.files.size()); + assertEquals(HttpPostRequestTest.VALUE_TEST_SIMPLE_RAW_DATA_WITH_AMPHASIS, this.testServer.files.get(HttpPostRequestTest.POST_RAW_CONTENT_FILE_ENTRY)); } } diff --git a/core/src/test/java/fi/iki/elonen/HttpPutRequestTest.java b/core/src/test/java/fi/iki/elonen/HttpPutRequestTest.java index 912113e..54a3343 100644 --- a/core/src/test/java/fi/iki/elonen/HttpPutRequestTest.java +++ b/core/src/test/java/fi/iki/elonen/HttpPutRequestTest.java @@ -1,39 +1,72 @@ package fi.iki.elonen; -import org.junit.Test; +/* + * #%L + * NanoHttpd-Core + * %% + * Copyright (C) 2012 - 2015 nanohttpd + * %% + * Redistribution and use in source and binary forms, with or without modification, + * are permitted provided that the following conditions are met: + * + * 1. Redistributions of source code must retain the above copyright notice, this + * list of conditions and the following disclaimer. + * + * 2. Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * 3. Neither the name of the nanohttpd nor the names of its contributors + * may be used to endorse or promote products derived from this software without + * specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. + * IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, + * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, + * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF + * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE + * OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED + * OF THE POSSIBILITY OF SUCH DAMAGE. + * #L% + */ + +import static junit.framework.Assert.assertTrue; import java.io.BufferedReader; import java.io.ByteArrayOutputStream; import java.io.FileReader; import java.util.List; -import static junit.framework.Assert.*; +import org.junit.Test; public class HttpPutRequestTest extends HttpServerTest { @Test public void testPutRequestSendsContent() throws Exception { - ByteArrayOutputStream outputStream = invokeServer("PUT " + URI + " HTTP/1.1\r\n\r\nBodyData 1\nLine 2"); + ByteArrayOutputStream outputStream = invokeServer("PUT " + HttpServerTest.URI + " HTTP/1.1\r\n\r\nBodyData 1\nLine 2"); String[] expectedOutput = { - "HTTP/1.1 200 OK", - "Content-Type: text/html", - "Date: .*", - "Connection: keep-alive", - "Content-Length: 0", - "" + "HTTP/1.1 200 OK", + "Content-Type: text/html", + "Date: .*", + "Connection: keep-alive", + "Content-Length: 0", + "" }; assertResponse(outputStream, expectedOutput); - assertTrue(testServer.files.containsKey("content")); + assertTrue(this.testServer.files.containsKey("content")); BufferedReader reader = null; try { String[] expectedInputToServeMethodViaFile = { - "BodyData 1", - "Line 2" + "BodyData 1", + "Line 2" }; - reader = new BufferedReader(new FileReader(testServer.files.get("content"))); + reader = new BufferedReader(new FileReader(this.testServer.files.get("content"))); List<String> lines = readLinesFromFile(reader); assertLinesOfText(expectedInputToServeMethodViaFile, lines); } finally { diff --git a/core/src/test/java/fi/iki/elonen/HttpSSLServerTest.java b/core/src/test/java/fi/iki/elonen/HttpSSLServerTest.java new file mode 100644 index 0000000..30fb48c --- /dev/null +++ b/core/src/test/java/fi/iki/elonen/HttpSSLServerTest.java @@ -0,0 +1,89 @@ +package fi.iki.elonen; + +/* + * #%L + * NanoHttpd-Core + * %% + * Copyright (C) 2012 - 2015 nanohttpd + * %% + * Redistribution and use in source and binary forms, with or without modification, + * are permitted provided that the following conditions are met: + * + * 1. Redistributions of source code must retain the above copyright notice, this + * list of conditions and the following disclaimer. + * + * 2. Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * 3. Neither the name of the nanohttpd nor the names of its contributors + * may be used to endorse or promote products derived from this software without + * specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. + * IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, + * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, + * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF + * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE + * OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED + * OF THE POSSIBILITY OF SUCH DAMAGE. + * #L% + */ + +import java.io.File; +import java.io.IOException; + +import javax.net.ssl.SSLContext; + +import org.apache.http.HttpEntity; +import org.apache.http.HttpResponse; +import org.apache.http.client.ClientProtocolException; +import org.apache.http.client.methods.HttpTrace; +import org.apache.http.impl.client.DefaultHttpClient; +import org.junit.After; +import org.junit.Assert; +import org.junit.Before; +import org.junit.Test; + +public class HttpSSLServerTest extends HttpServerTest { + + @Test + public void testSSLConnection() throws ClientProtocolException, IOException { + DefaultHttpClient httpclient = new DefaultHttpClient(); + HttpTrace httphead = new HttpTrace("https://localhost:9043/index.html"); + HttpResponse response = httpclient.execute(httphead); + HttpEntity entity = response.getEntity(); + Assert.assertEquals(200, response.getStatusLine().getStatusCode()); + + Assert.assertEquals(9043, this.testServer.getListeningPort()); + Assert.assertTrue(this.testServer.isAlive()); + } + + @Before + public void setUp() throws Exception { + System.setProperty("javax.net.ssl.trustStore", new File("src/test/resources/keystore.jks").getAbsolutePath()); + this.testServer = new TestServer(9043); + this.testServer.makeSecure(NanoHTTPD.makeSSLSocketFactory("/keystore.jks", "password".toCharArray()), null); + this.tempFileManager = new TestTempFileManager(); + this.testServer.start(); + try { + long start = System.currentTimeMillis(); + Thread.sleep(100L); + while (!this.testServer.wasStarted()) { + Thread.sleep(100L); + if (System.currentTimeMillis() - start > 2000) { + Assert.fail("could not start server"); + } + } + } catch (InterruptedException e) { + } + } + + @After + public void tearDown() { + this.testServer.stop(); + } +} diff --git a/core/src/test/java/fi/iki/elonen/HttpServerTest.java b/core/src/test/java/fi/iki/elonen/HttpServerTest.java index ef209d1..e8be61e 100644 --- a/core/src/test/java/fi/iki/elonen/HttpServerTest.java +++ b/core/src/test/java/fi/iki/elonen/HttpServerTest.java @@ -1,41 +1,143 @@ package fi.iki.elonen; -import org.junit.After; -import org.junit.Before; -import org.junit.Test; +/* + * #%L + * NanoHttpd-Core + * %% + * Copyright (C) 2012 - 2015 nanohttpd + * %% + * Redistribution and use in source and binary forms, with or without modification, + * are permitted provided that the following conditions are met: + * + * 1. Redistributions of source code must retain the above copyright notice, this + * list of conditions and the following disclaimer. + * + * 2. Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * 3. Neither the name of the nanohttpd nor the names of its contributors + * may be used to endorse or promote products derived from this software without + * specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. + * IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, + * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, + * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF + * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE + * OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED + * OF THE POSSIBILITY OF SUCH DAMAGE. + * #L% + */ -import java.io.*; +import static junit.framework.Assert.assertNotNull; +import static junit.framework.Assert.assertTrue; +import static junit.framework.Assert.fail; + +import java.io.BufferedReader; +import java.io.ByteArrayInputStream; +import java.io.ByteArrayOutputStream; +import java.io.IOException; +import java.io.InputStream; +import java.io.OutputStream; +import java.io.StringReader; import java.net.InetAddress; import java.util.ArrayList; import java.util.HashMap; import java.util.List; import java.util.Map; -import static junit.framework.Assert.*; +import org.junit.After; +import org.junit.Before; +import org.junit.Test; /** - * @author Paul S. Hawke (paul.hawke@gmail.com) - * On: 3/10/13 at 8:32 PM + * @author Paul S. Hawke (paul.hawke@gmail.com) On: 3/10/13 at 8:32 PM */ public class HttpServerTest { - public static final String URI = "http://www.myserver.org/pub/WWW/someFile.html"; - protected TestServer testServer; - private TestTempFileManager tempFileManager; - @Before - public void setUp() { - testServer = new TestServer(); - tempFileManager = new TestTempFileManager(); + public static class TestServer extends NanoHTTPD { + + public Response response = newFixedLengthResponse(""); + + public String uri; + + public Method method; + + public Map<String, String> header; + + public Map<String, String> parms; + + public Map<String, String> files; + + public Map<String, List<String>> decodedParamters; + + public Map<String, List<String>> decodedParamtersFromParameter; + + public String queryParameterString; + + public TestServer() { + super(8192); + } + + public TestServer(int port) { + super(port); + } + + public HTTPSession createSession(TempFileManager tempFileManager, InputStream inputStream, OutputStream outputStream) { + return new HTTPSession(tempFileManager, inputStream, outputStream); + } + + public HTTPSession createSession(TempFileManager tempFileManager, InputStream inputStream, OutputStream outputStream, InetAddress inetAddress) { + return new HTTPSession(tempFileManager, inputStream, outputStream, inetAddress); + } + + @Override + public Response serve(IHTTPSession session) { + this.uri = session.getUri(); + this.method = session.getMethod(); + this.header = session.getHeaders(); + this.parms = session.getParms(); + this.files = new HashMap<String, String>(); + try { + session.parseBody(this.files); + } catch (Exception e) { + e.printStackTrace(); + } + this.queryParameterString = session.getQueryParameterString(); + this.decodedParamtersFromParameter = decodeParameters(this.queryParameterString); + this.decodedParamters = decodeParameters(session.getQueryParameterString()); + return this.response; + } } - @After - public void tearDown() { - tempFileManager._clear(); + public static class TestTempFileManager extends NanoHTTPD.DefaultTempFileManager { + + public void _clear() { + super.clear(); + } + + @Override + public void clear() { + // ignore + } } - @Test - public void testServerExists() { - assertNotNull(testServer); + public static final String URI = "http://www.myserver.org/pub/WWW/someFile.html"; + + protected TestServer testServer; + + protected TestTempFileManager tempFileManager; + + protected void assertLinesOfText(String[] expected, List<String> lines) { + // assertEquals(expected.length, lines.size()); + for (int i = 0; i < expected.length; i++) { + String line = lines.get(i); + assertTrue("Output line " + i + " doesn't match expectation.\n" + " Output: " + line + "\n" + "Expected: " + expected[i], line.matches(expected[i])); + } } protected void assertResponse(ByteArrayOutputStream outputStream, String[] expected) throws IOException { @@ -43,34 +145,24 @@ public class HttpServerTest { assertLinesOfText(expected, lines); } - protected void assertLinesOfText(String[] expected, List<String> lines) { -// assertEquals(expected.length, lines.size()); - for (int i = 0; i < expected.length; i++) { - String line = lines.get(i); - assertTrue("Output line " + i + " doesn't match expectation.\n" + - " Output: " + line + "\n" + - "Expected: " + expected[i], line.matches(expected[i])); - } + protected List<String> getOutputLines(ByteArrayOutputStream outputStream) throws IOException { + BufferedReader reader = new BufferedReader(new StringReader(outputStream.toString())); + return readLinesFromFile(reader); } protected ByteArrayOutputStream invokeServer(String request) { ByteArrayInputStream inputStream = new ByteArrayInputStream(request.getBytes()); ByteArrayOutputStream outputStream = new ByteArrayOutputStream(); - NanoHTTPD.HTTPSession session = testServer.createSession(tempFileManager, inputStream, outputStream); + NanoHTTPD.HTTPSession session = this.testServer.createSession(this.tempFileManager, inputStream, outputStream); try { session.execute(); } catch (IOException e) { - fail(""+e); + fail("" + e); e.printStackTrace(); } return outputStream; } - protected List<String> getOutputLines(ByteArrayOutputStream outputStream) throws IOException { - BufferedReader reader = new BufferedReader(new StringReader(outputStream.toString())); - return readLinesFromFile(reader); - } - protected List<String> readLinesFromFile(BufferedReader reader) throws IOException { List<String> lines = new ArrayList<String>(); String line = ""; @@ -83,60 +175,19 @@ public class HttpServerTest { return lines; } - public static class TestTempFileManager extends NanoHTTPD.DefaultTempFileManager { - public void _clear() { - super.clear(); - } - - @Override - public void clear() { - // ignore - } + @Before + public void setUp() throws Exception { + this.testServer = new TestServer(); + this.tempFileManager = new TestTempFileManager(); } - public static class TestServer extends NanoHTTPD { - public Response response = new Response(""); - public String uri; - public Method method; - public Map<String, String> header; - public Map<String, String> parms; - public Map<String, String> files; - public Map<String, List<String>> decodedParamters; - public Map<String, List<String>> decodedParamtersFromParameter; - public String queryParameterString; - - public TestServer() { - super(8192); - } - - public HTTPSession createSession(TempFileManager tempFileManager, InputStream inputStream, OutputStream outputStream) { - return new HTTPSession(tempFileManager, inputStream, outputStream); - } - - public HTTPSession createSession(TempFileManager tempFileManager, InputStream inputStream, OutputStream outputStream, InetAddress inetAddress) { - return new HTTPSession(tempFileManager, inputStream, outputStream, inetAddress); - } - - @Override public Response serve(IHTTPSession session) { - this.uri = session.getUri(); - this.method = session.getMethod(); - this.header = session.getHeaders(); - this.parms = session.getParms(); - this.files = new HashMap<String, String>(); - try { - session.parseBody(files); - } catch (Exception e) { - e.printStackTrace(); - } - queryParameterString = session.getQueryParameterString(); - this.decodedParamtersFromParameter = decodeParameters(queryParameterString); - this.decodedParamters = decodeParameters(session.getQueryParameterString()); - return response; - } + @After + public void tearDown() { + this.tempFileManager._clear(); + } - @Override - public String decodePercent(String str) { - return super.decodePercent(str); - } + @Test + public void testServerExists() { + assertNotNull(this.testServer); } } diff --git a/core/src/test/java/fi/iki/elonen/HttpSessionHeadersTest.java b/core/src/test/java/fi/iki/elonen/HttpSessionHeadersTest.java index 75a0a49..1494e28 100644 --- a/core/src/test/java/fi/iki/elonen/HttpSessionHeadersTest.java +++ b/core/src/test/java/fi/iki/elonen/HttpSessionHeadersTest.java @@ -1,30 +1,66 @@ package fi.iki.elonen; -import org.junit.Test; +/* + * #%L + * NanoHttpd-Core + * %% + * Copyright (C) 2012 - 2015 nanohttpd + * %% + * Redistribution and use in source and binary forms, with or without modification, + * are permitted provided that the following conditions are met: + * + * 1. Redistributions of source code must retain the above copyright notice, this + * list of conditions and the following disclaimer. + * + * 2. Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * 3. Neither the name of the nanohttpd nor the names of its contributors + * may be used to endorse or promote products derived from this software without + * specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. + * IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, + * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, + * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF + * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE + * OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED + * OF THE POSSIBILITY OF SUCH DAMAGE. + * #L% + */ + +import static org.junit.Assert.assertEquals; import java.io.ByteArrayInputStream; import java.io.ByteArrayOutputStream; import java.net.InetAddress; -import static org.junit.Assert.assertEquals; +import org.junit.Ignore; +import org.junit.Test; public class HttpSessionHeadersTest extends HttpServerTest { + private static final String DUMMY_REQUEST_CONTENT = "dummy request content"; - private static final TestTempFileManager TEST_TEMP_FILE_MANAGER = new TestTempFileManager(); - @Override - public void setUp() { - super.setUp(); - } + private static final TestTempFileManager TEST_TEMP_FILE_MANAGER = new TestTempFileManager(); @Test + @Ignore public void testHeadersRemoteIp() throws Exception { - ByteArrayInputStream inputStream = new ByteArrayInputStream(DUMMY_REQUEST_CONTENT.getBytes()); + ByteArrayInputStream inputStream = new ByteArrayInputStream(HttpSessionHeadersTest.DUMMY_REQUEST_CONTENT.getBytes()); ByteArrayOutputStream outputStream = new ByteArrayOutputStream(); - String[] ipAddresses = { "127.0.0.1", "192.168.1.1", "192.30.252.129" }; - for(String ipAddress : ipAddresses) { + String[] ipAddresses = { + "127.0.0.1", + "192.168.1.1", + "192.30.252.129" + }; + for (String ipAddress : ipAddresses) { InetAddress inetAddress = InetAddress.getByName(ipAddress); - NanoHTTPD.HTTPSession session = testServer.createSession(TEST_TEMP_FILE_MANAGER, inputStream, outputStream, inetAddress); + NanoHTTPD.HTTPSession session = this.testServer.createSession(HttpSessionHeadersTest.TEST_TEMP_FILE_MANAGER, inputStream, outputStream, inetAddress); assertEquals(ipAddress, session.getHeaders().get("remote-addr")); assertEquals(ipAddress, session.getHeaders().get("http-client-ip")); } diff --git a/core/src/test/java/fi/iki/elonen/InvalidRequestTest.java b/core/src/test/java/fi/iki/elonen/InvalidRequestTest.java new file mode 100644 index 0000000..eda60a3 --- /dev/null +++ b/core/src/test/java/fi/iki/elonen/InvalidRequestTest.java @@ -0,0 +1,79 @@ +package fi.iki.elonen; + +/* + * #%L + * NanoHttpd-Core + * %% + * Copyright (C) 2012 - 2015 nanohttpd + * %% + * Redistribution and use in source and binary forms, with or without modification, + * are permitted provided that the following conditions are met: + * + * 1. Redistributions of source code must retain the above copyright notice, this + * list of conditions and the following disclaimer. + * + * 2. Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * 3. Neither the name of the nanohttpd nor the names of its contributors + * may be used to endorse or promote products derived from this software without + * specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. + * IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, + * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, + * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF + * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE + * OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED + * OF THE POSSIBILITY OF SUCH DAMAGE. + * #L% + */ +import static junit.framework.Assert.assertNotNull; +import static junit.framework.Assert.assertTrue; + +import org.junit.Test; + +public class InvalidRequestTest extends HttpServerTest { + + @Test + public void testGetRequestWithoutProtocol() { + invokeServer("GET " + HttpServerTest.URI + "\r\nX-Important-Header: foo"); + + assertNotNull(this.testServer.parms); + assertTrue(this.testServer.header.size() > 0); + assertNotNull(this.testServer.files); + assertNotNull(this.testServer.uri); + } + + @Test + public void testGetRequestWithProtocol() { + invokeServer("GET " + HttpServerTest.URI + " HTTP/1.1\r\nX-Important-Header: foo"); + + assertNotNull(this.testServer.parms); + assertTrue(this.testServer.header.size() > 0); + assertNotNull(this.testServer.files); + assertNotNull(this.testServer.uri); + } + + @Test + public void testPostRequestWithoutProtocol() { + invokeServer("POST " + HttpServerTest.URI + "\r\nContent-Length: 123"); + assertNotNull(this.testServer.parms); + assertTrue(this.testServer.header.size() > 0); + assertNotNull(this.testServer.files); + assertNotNull(this.testServer.uri); + } + + @Test + public void testPostRequestWithProtocol() { + invokeServer("POST " + HttpServerTest.URI + " HTTP/1.1\r\nContent-Length: 123"); + assertNotNull(this.testServer.parms); + assertTrue(this.testServer.header.size() > 0); + assertNotNull(this.testServer.files); + assertNotNull(this.testServer.uri); + } +} diff --git a/core/src/test/java/fi/iki/elonen/JavaIOTempDirExistTest.java b/core/src/test/java/fi/iki/elonen/JavaIOTempDirExistTest.java new file mode 100644 index 0000000..b586bc2 --- /dev/null +++ b/core/src/test/java/fi/iki/elonen/JavaIOTempDirExistTest.java @@ -0,0 +1,87 @@ +package fi.iki.elonen; + +/* + * #%L + * NanoHttpd-Core + * %% + * Copyright (C) 2012 - 2015 nanohttpd + * %% + * Redistribution and use in source and binary forms, with or without modification, + * are permitted provided that the following conditions are met: + * + * 1. Redistributions of source code must retain the above copyright notice, this + * list of conditions and the following disclaimer. + * + * 2. Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * 3. Neither the name of the nanohttpd nor the names of its contributors + * may be used to endorse or promote products derived from this software without + * specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. + * IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, + * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, + * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF + * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE + * OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED + * OF THE POSSIBILITY OF SUCH DAMAGE. + * #L% + */ + +import java.io.File; +import java.io.IOException; +import java.util.UUID; + +import org.junit.Assert; +import org.junit.Test; + +import fi.iki.elonen.NanoHTTPD.DefaultTempFile; + +/** + * Created by Victor Nikiforov on 10/16/15. + */ +public class JavaIOTempDirExistTest { + + @Test + public void testJavaIoTempDefault() throws Exception { + String tmpdir = System.getProperty("java.io.tmpdir"); + NanoHTTPD.DefaultTempFileManager manager = new NanoHTTPD.DefaultTempFileManager(); + DefaultTempFile tempFile = (DefaultTempFile) manager.createTempFile("xx"); + File tempFileBackRef = new File(tempFile.getName()); + Assert.assertEquals(tempFileBackRef.getParentFile(), new File(tmpdir)); + + // force an exception + tempFileBackRef.delete(); + Exception e = null; + try { + tempFile.delete(); + } catch (Exception ex) { + e = ex; + } + Assert.assertNotNull(e); + manager.clear(); + } + + @Test + public void testJavaIoTempSpecific() throws IOException { + final String tmpdir = System.getProperty("java.io.tmpdir"); + try { + String tempFileName = UUID.randomUUID().toString(); + File newDir = new File("target", tempFileName); + System.setProperty("java.io.tmpdir", newDir.getAbsolutePath()); + Assert.assertEquals(false, newDir.exists()); + new NanoHTTPD.DefaultTempFileManager(); + Assert.assertEquals(true, newDir.exists()); + newDir.delete(); + } finally { + System.setProperty("java.io.tmpdir", tmpdir); + } + + } + +} diff --git a/core/src/test/java/fi/iki/elonen/MimeTest.java b/core/src/test/java/fi/iki/elonen/MimeTest.java new file mode 100644 index 0000000..046ef00 --- /dev/null +++ b/core/src/test/java/fi/iki/elonen/MimeTest.java @@ -0,0 +1,62 @@ +package fi.iki.elonen; + +/* + * #%L + * NanoHttpd-Core + * %% + * Copyright (C) 2012 - 2015 nanohttpd + * %% + * Redistribution and use in source and binary forms, with or without modification, + * are permitted provided that the following conditions are met: + * + * 1. Redistributions of source code must retain the above copyright notice, this + * list of conditions and the following disclaimer. + * + * 2. Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * 3. Neither the name of the nanohttpd nor the names of its contributors + * may be used to endorse or promote products derived from this software without + * specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. + * IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, + * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, + * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF + * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE + * OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED + * OF THE POSSIBILITY OF SUCH DAMAGE. + * #L% + */ + +import org.junit.Assert; +import org.junit.Test; + +public class MimeTest { + + @Test + public void testExistingMimeType() throws Exception { + Assert.assertEquals("text/html", NanoHTTPD.getMimeTypeForFile("xxxx.html")); + } + + @Test + public void testNotExistingMimeType() throws Exception { + Assert.assertNull(NanoHTTPD.mimeTypes().get("notExistent")); + Assert.assertEquals("application/octet-stream", NanoHTTPD.getMimeTypeForFile("xxxx.notExistent")); + } + + @Test + public void testOverwritenMimeType() throws Exception { + Assert.assertEquals("video/wrongOverwrite", NanoHTTPD.getMimeTypeForFile("xxxx.ts")); + } + + @Test + public void testManualMimeType() throws Exception { + NanoHTTPD.mimeTypes().put("flv", "video/manualOverwrite"); + Assert.assertEquals("video/manualOverwrite", NanoHTTPD.getMimeTypeForFile("xxxx.flv")); + } +} diff --git a/core/src/test/java/fi/iki/elonen/SSLServerSocketFactoryTest.java b/core/src/test/java/fi/iki/elonen/SSLServerSocketFactoryTest.java new file mode 100644 index 0000000..1722058 --- /dev/null +++ b/core/src/test/java/fi/iki/elonen/SSLServerSocketFactoryTest.java @@ -0,0 +1,90 @@ +package fi.iki.elonen; + +import java.io.File; + +/* + * #%L + * NanoHttpd-Core + * %% + * Copyright (C) 2012 - 2015 nanohttpd + * %% + * Redistribution and use in source and binary forms, with or without modification, + * are permitted provided that the following conditions are met: + * + * 1. Redistributions of source code must retain the above copyright notice, this + * list of conditions and the following disclaimer. + * + * 2. Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * 3. Neither the name of the nanohttpd nor the names of its contributors + * may be used to endorse or promote products derived from this software without + * specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. + * IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, + * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, + * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF + * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE + * OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED + * OF THE POSSIBILITY OF SUCH DAMAGE. + * #L% + */ + +import java.io.IOException; + +import org.apache.http.HttpEntity; +import org.apache.http.HttpResponse; +import org.apache.http.client.ClientProtocolException; +import org.apache.http.client.methods.HttpTrace; +import org.apache.http.impl.client.DefaultHttpClient; +import org.junit.After; +import org.junit.Assert; +import org.junit.Before; +import org.junit.Test; + +import fi.iki.elonen.NanoHTTPD.SecureServerSocketFactory; + +public class SSLServerSocketFactoryTest extends HttpServerTest { + + @Test + public void testSSLConnection() throws ClientProtocolException, IOException { + DefaultHttpClient httpclient = new DefaultHttpClient(); + HttpTrace httphead = new HttpTrace("https://localhost:9043/index.html"); + HttpResponse response = httpclient.execute(httphead); + HttpEntity entity = response.getEntity(); + Assert.assertEquals(200, response.getStatusLine().getStatusCode()); + + Assert.assertEquals(9043, this.testServer.getListeningPort()); + Assert.assertTrue(this.testServer.isAlive()); + } + + @Before + public void setUp() throws Exception { + System.setProperty("javax.net.ssl.trustStore", new File("src/test/resources/keystore.jks").getAbsolutePath()); + this.testServer = new TestServer(9043); + this.testServer.setServerSocketFactory(new SecureServerSocketFactory(NanoHTTPD.makeSSLSocketFactory("/keystore.jks", "password".toCharArray()), null)); + this.tempFileManager = new TestTempFileManager(); + this.testServer.start(); + try { + long start = System.currentTimeMillis(); + Thread.sleep(100L); + while (!this.testServer.wasStarted()) { + Thread.sleep(100L); + if (System.currentTimeMillis() - start > 2000) { + Assert.fail("could not start server"); + } + } + } catch (InterruptedException e) { + } + } + + @After + public void tearDown() { + this.testServer.stop(); + } +} diff --git a/core/src/test/java/fi/iki/elonen/ServerSocketFactoryTest.java b/core/src/test/java/fi/iki/elonen/ServerSocketFactoryTest.java new file mode 100644 index 0000000..17112ef --- /dev/null +++ b/core/src/test/java/fi/iki/elonen/ServerSocketFactoryTest.java @@ -0,0 +1,102 @@ +package fi.iki.elonen; + +import java.io.File; + +/* + * #%L + * NanoHttpd-Core + * %% + * Copyright (C) 2012 - 2015 nanohttpd + * %% + * Redistribution and use in source and binary forms, with or without modification, + * are permitted provided that the following conditions are met: + * + * 1. Redistributions of source code must retain the above copyright notice, this + * list of conditions and the following disclaimer. + * + * 2. Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * 3. Neither the name of the nanohttpd nor the names of its contributors + * may be used to endorse or promote products derived from this software without + * specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. + * IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, + * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, + * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF + * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE + * OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED + * OF THE POSSIBILITY OF SUCH DAMAGE. + * #L% + */ + +import java.io.IOException; +import java.net.ServerSocket; + +import org.junit.Assert; +import org.junit.Test; + +import fi.iki.elonen.HttpServerTest.TestServer; +import fi.iki.elonen.NanoHTTPD.SecureServerSocketFactory; + +public class ServerSocketFactoryTest extends NanoHTTPD { + + public static final int PORT = 8192; + + public ServerSocketFactoryTest() { + super(PORT); + + this.setServerSocketFactory(new TestFactory()); + } + + @Test + public void isCustomServerSocketFactory() { + System.out.println("CustomServerSocketFactory test"); + Assert.assertTrue(this.getServerSocketFactory() instanceof TestFactory); + } + + @Test + public void testCreateServerSocket() { + System.out.println("CreateServerSocket test"); + ServerSocket ss = null; + try { + ss = this.getServerSocketFactory().create(); + } catch (IOException e) { + } + Assert.assertTrue(ss != null); + } + + @Test + public void testSSLServerSocketFail() { + String[] protocols = { + "" + }; + System.setProperty("javax.net.ssl.trustStore", new File("src/test/resources/keystore.jks").getAbsolutePath()); + ServerSocketFactory ssFactory = new SecureServerSocketFactory(null, protocols); + ServerSocket ss = null; + try { + ss = ssFactory.create(); + } catch (Exception e) { + } + Assert.assertTrue(ss == null); + + } + + private class TestFactory implements ServerSocketFactory { + + @Override + public ServerSocket create() { + try { + return new ServerSocket(); + } catch (IOException e) { + e.printStackTrace(); + } + return null; + } + } +} diff --git a/core/src/test/java/fi/iki/elonen/integration/CookieIntegrationTest.java b/core/src/test/java/fi/iki/elonen/integration/CookieIntegrationTest.java index 0d54b37..5cf5719 100644 --- a/core/src/test/java/fi/iki/elonen/integration/CookieIntegrationTest.java +++ b/core/src/test/java/fi/iki/elonen/integration/CookieIntegrationTest.java @@ -1,6 +1,45 @@ package fi.iki.elonen.integration; -import fi.iki.elonen.NanoHTTPD; +/* + * #%L + * NanoHttpd-Core + * %% + * Copyright (C) 2012 - 2015 nanohttpd + * %% + * Redistribution and use in source and binary forms, with or without modification, + * are permitted provided that the following conditions are met: + * + * 1. Redistributions of source code must retain the above copyright notice, this + * list of conditions and the following disclaimer. + * + * 2. Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * 3. Neither the name of the nanohttpd nor the names of its contributors + * may be used to endorse or promote products derived from this software without + * specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. + * IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, + * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, + * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF + * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE + * OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED + * OF THE POSSIBILITY OF SUCH DAMAGE. + * #L% + */ + +import static org.junit.Assert.assertEquals; +import static org.junit.Assert.assertTrue; + +import java.util.ArrayList; +import java.util.Calendar; +import java.util.List; + import org.apache.http.client.CookieStore; import org.apache.http.client.ResponseHandler; import org.apache.http.client.methods.HttpGet; @@ -8,78 +47,77 @@ import org.apache.http.impl.client.BasicResponseHandler; import org.apache.http.impl.cookie.BasicClientCookie; import org.junit.Test; -import java.util.ArrayList; -import java.util.Calendar; -import java.util.List; - -import static org.junit.Assert.*; +import fi.iki.elonen.NanoHTTPD; /** - * @author Paul S. Hawke (paul.hawke@gmail.com) - * On: 9/2/13 at 10:10 PM + * @author Paul S. Hawke (paul.hawke@gmail.com) On: 9/2/13 at 10:10 PM */ public class CookieIntegrationTest extends IntegrationTestBase<CookieIntegrationTest.CookieTestServer> { - @Test - public void testNoCookies() throws Exception { - HttpGet httpget = new HttpGet("http://localhost:8192/"); - ResponseHandler<String> responseHandler = new BasicResponseHandler(); - httpclient.execute(httpget, responseHandler); + public static class CookieTestServer extends NanoHTTPD { - CookieStore cookies = httpclient.getCookieStore(); - assertEquals(0, cookies.getCookies().size()); + List<Cookie> cookiesReceived = new ArrayList<Cookie>(); + + List<Cookie> cookiesToSend = new ArrayList<Cookie>(); + + public CookieTestServer() { + super(8192); + } + + @Override + public Response serve(IHTTPSession session) { + CookieHandler cookies = session.getCookies(); + for (String cookieName : cookies) { + this.cookiesReceived.add(new Cookie(cookieName, cookies.read(cookieName))); + } + for (Cookie c : this.cookiesToSend) { + cookies.set(c); + } + return newFixedLengthResponse("Cookies!"); + } + } + + @Override + public CookieTestServer createTestServer() { + return new CookieTestServer(); } @Test public void testCookieSentBackToClient() throws Exception { - testServer.cookiesToSend.add(new NanoHTTPD.Cookie("name", "value", 30)); + this.testServer.cookiesToSend.add(new NanoHTTPD.Cookie("name", "value", 30)); HttpGet httpget = new HttpGet("http://localhost:8192/"); ResponseHandler<String> responseHandler = new BasicResponseHandler(); - httpclient.execute(httpget, responseHandler); + this.httpclient.execute(httpget, responseHandler); - CookieStore cookies = httpclient.getCookieStore(); + CookieStore cookies = this.httpclient.getCookieStore(); assertEquals(1, cookies.getCookies().size()); assertEquals("name", cookies.getCookies().get(0).getName()); assertEquals("value", cookies.getCookies().get(0).getValue()); } @Test + public void testNoCookies() throws Exception { + HttpGet httpget = new HttpGet("http://localhost:8192/"); + ResponseHandler<String> responseHandler = new BasicResponseHandler(); + this.httpclient.execute(httpget, responseHandler); + + CookieStore cookies = this.httpclient.getCookieStore(); + assertEquals(0, cookies.getCookies().size()); + } + + @Test public void testServerReceivesCookiesSentFromClient() throws Exception { BasicClientCookie clientCookie = new BasicClientCookie("name", "value"); Calendar calendar = Calendar.getInstance(); calendar.add(Calendar.DAY_OF_YEAR, 100); clientCookie.setExpiryDate(calendar.getTime()); clientCookie.setDomain("localhost"); - httpclient.getCookieStore().addCookie(clientCookie); + this.httpclient.getCookieStore().addCookie(clientCookie); HttpGet httpget = new HttpGet("http://localhost:8192/"); ResponseHandler<String> responseHandler = new BasicResponseHandler(); - httpclient.execute(httpget, responseHandler); + this.httpclient.execute(httpget, responseHandler); - assertEquals(1, testServer.cookiesReceived.size()); - assertTrue(testServer.cookiesReceived.get(0).getHTTPHeader().contains("name=value")); - } - - @Override public CookieTestServer createTestServer() { - return new CookieTestServer(); - } - - public static class CookieTestServer extends NanoHTTPD { - List<Cookie> cookiesReceived = new ArrayList<Cookie>(); - List<Cookie> cookiesToSend = new ArrayList<Cookie>(); - - public CookieTestServer() { - super(8192); - } - - @Override public Response serve(IHTTPSession session) { - CookieHandler cookies = session.getCookies(); - for (String cookieName : cookies) { - cookiesReceived.add(new Cookie(cookieName, cookies.read(cookieName))); - } - for (Cookie c : cookiesToSend) { - cookies.set(c); - } - return new Response("Cookies!"); - } + assertEquals(1, this.testServer.cookiesReceived.size()); + assertTrue(this.testServer.cookiesReceived.get(0).getHTTPHeader().contains("name=value")); } } diff --git a/core/src/test/java/fi/iki/elonen/integration/GZipIntegrationTest.java b/core/src/test/java/fi/iki/elonen/integration/GZipIntegrationTest.java new file mode 100644 index 0000000..a278406 --- /dev/null +++ b/core/src/test/java/fi/iki/elonen/integration/GZipIntegrationTest.java @@ -0,0 +1,168 @@ +package fi.iki.elonen.integration; + +/* + * #%L + * NanoHttpd-Core + * %% + * Copyright (C) 2012 - 2015 nanohttpd + * %% + * Redistribution and use in source and binary forms, with or without modification, + * are permitted provided that the following conditions are met: + * + * 1. Redistributions of source code must retain the above copyright notice, this + * list of conditions and the following disclaimer. + * + * 2. Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * 3. Neither the name of the nanohttpd nor the names of its contributors + * may be used to endorse or promote products derived from this software without + * specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. + * IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, + * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, + * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF + * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE + * OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED + * OF THE POSSIBILITY OF SUCH DAMAGE. + * #L% + */ + +import static org.hamcrest.CoreMatchers.is; +import static org.hamcrest.CoreMatchers.nullValue; +import static org.junit.Assert.assertEquals; +import static org.junit.Assert.assertNotNull; +import static org.junit.Assert.assertNull; +import static org.junit.Assert.assertThat; + +import java.io.ByteArrayInputStream; +import java.io.IOException; +import java.io.InputStream; + +import org.apache.http.Header; +import org.apache.http.HttpResponse; +import org.apache.http.client.methods.HttpGet; +import org.apache.http.impl.client.DecompressingHttpClient; +import org.apache.http.util.EntityUtils; +import org.junit.Test; + +import fi.iki.elonen.NanoHTTPD; + +public class GZipIntegrationTest extends IntegrationTestBase<GZipIntegrationTest.TestServer> { + + public static class TestServer extends NanoHTTPD { + + public Response response; + + public TestServer() { + super(8192); + } + + @Override + public Response serve(IHTTPSession session) { + return response; + } + + @Override + protected boolean useGzipWhenAccepted(Response r) { + return true; + } + } + + @Override + public TestServer createTestServer() { + return new TestServer(); + } + + @Test + public void contentEncodingShouldBeAddedToFixedLengthResponses() throws IOException { + testServer.response = NanoHTTPD.newFixedLengthResponse("This is a test"); + HttpGet request = new HttpGet("http://localhost:8192/"); + request.addHeader("Accept-encoding", "gzip"); + HttpResponse response = httpclient.execute(request); + Header contentEncoding = response.getFirstHeader("content-encoding"); + assertNotNull("Content-Encoding should be set", contentEncoding); + assertEquals("gzip", contentEncoding.getValue()); + } + + @Test + public void contentEncodingShouldBeAddedToChunkedResponses() throws IOException { + InputStream data = new ByteArrayInputStream("This is a test".getBytes("UTF-8")); + testServer.response = NanoHTTPD.newChunkedResponse(NanoHTTPD.Response.Status.OK, "text/plain", data); + HttpGet request = new HttpGet("http://localhost:8192/"); + request.addHeader("Accept-encoding", "gzip"); + HttpResponse response = httpclient.execute(request); + Header contentEncoding = response.getFirstHeader("content-encoding"); + assertNotNull("Content-Encoding should be set", contentEncoding); + assertEquals("gzip", contentEncoding.getValue()); + } + + @Test + public void shouldFindCorrectAcceptEncodingAmongMany() throws IOException { + testServer.response = NanoHTTPD.newFixedLengthResponse("This is a test"); + HttpGet request = new HttpGet("http://localhost:8192/"); + request.addHeader("Accept-encoding", "deflate,gzip"); + HttpResponse response = httpclient.execute(request); + Header contentEncoding = response.getFirstHeader("content-encoding"); + assertNotNull("Content-Encoding should be set", contentEncoding); + assertEquals("gzip", contentEncoding.getValue()); + } + + @Test + public void contentLengthShouldBeRemovedFromZippedResponses() throws IOException { + testServer.response = NanoHTTPD.newFixedLengthResponse("This is a test"); + HttpGet request = new HttpGet("http://localhost:8192/"); + request.addHeader("Accept-encoding", "gzip"); + HttpResponse response = httpclient.execute(request); + Header contentLength = response.getFirstHeader("content-length"); + assertNull("Content-Length should not be set when gzipping response", contentLength); + } + + @Test + public void fixedLengthContentIsEncodedProperly() throws IOException { + testServer.response = NanoHTTPD.newFixedLengthResponse("This is a test"); + HttpGet request = new HttpGet("http://localhost:8192/"); + request.addHeader("Accept-encoding", "gzip"); + HttpResponse response = new DecompressingHttpClient(httpclient).execute(request); + assertEquals("This is a test", EntityUtils.toString(response.getEntity())); + } + + @Test + public void chunkedContentIsEncodedProperly() throws IOException { + InputStream data = new ByteArrayInputStream("This is a test".getBytes("UTF-8")); + testServer.response = NanoHTTPD.newChunkedResponse(NanoHTTPD.Response.Status.OK, "text/plain", data); + HttpGet request = new HttpGet("http://localhost:8192/"); + request.addHeader("Accept-encoding", "gzip"); + HttpResponse response = new DecompressingHttpClient(httpclient).execute(request); + assertEquals("This is a test", EntityUtils.toString(response.getEntity())); + } + + @Test + public void noGzipWithoutAcceptEncoding() throws IOException { + testServer.response = NanoHTTPD.newFixedLengthResponse("This is a test"); + HttpGet request = new HttpGet("http://localhost:8192/"); + HttpResponse response = httpclient.execute(request); + Header contentEncoding = response.getFirstHeader("content-encoding"); + assertThat(contentEncoding, is(nullValue())); + assertEquals("This is a test", EntityUtils.toString(response.getEntity())); + } + + @Test + public void contentShouldNotBeGzippedIfContentLengthIsAddedManually() throws IOException { + testServer.response = NanoHTTPD.newFixedLengthResponse("This is a test"); + testServer.response.addHeader("Content-Length", "" + ("This is a test".getBytes("UTF-8").length)); + HttpGet request = new HttpGet("http://localhost:8192/"); + request.addHeader("Accept-encoding", "gzip"); + HttpResponse response = httpclient.execute(request); + Header contentEncoding = response.getFirstHeader("content-encoding"); + assertNull("Content-Encoding should not be set when manually setting content-length", contentEncoding); + assertEquals("This is a test", EntityUtils.toString(response.getEntity())); + + } + +} diff --git a/core/src/test/java/fi/iki/elonen/integration/GetAndPostIntegrationTest.java b/core/src/test/java/fi/iki/elonen/integration/GetAndPostIntegrationTest.java index bc0a9d9..eef2f22 100644 --- a/core/src/test/java/fi/iki/elonen/integration/GetAndPostIntegrationTest.java +++ b/core/src/test/java/fi/iki/elonen/integration/GetAndPostIntegrationTest.java @@ -1,8 +1,49 @@ package fi.iki.elonen.integration; -import fi.iki.elonen.NanoHTTPD; +/* + * #%L + * NanoHttpd-Core + * %% + * Copyright (C) 2012 - 2015 nanohttpd + * %% + * Redistribution and use in source and binary forms, with or without modification, + * are permitted provided that the following conditions are met: + * + * 1. Redistributions of source code must retain the above copyright notice, this + * list of conditions and the following disclaimer. + * + * 2. Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * 3. Neither the name of the nanohttpd nor the names of its contributors + * may be used to endorse or promote products derived from this software without + * specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. + * IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, + * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, + * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF + * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE + * OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED + * OF THE POSSIBILITY OF SUCH DAMAGE. + * #L% + */ + +import static org.junit.Assert.assertEquals; + +import java.nio.charset.Charset; +import java.util.ArrayList; +import java.util.Collections; +import java.util.List; +import java.util.Map; + +import org.apache.http.HttpEntity; +import org.apache.http.HttpResponse; import org.apache.http.NameValuePair; -import org.apache.http.client.HttpClient; import org.apache.http.client.ResponseHandler; import org.apache.http.client.entity.UrlEncodedFormEntity; import org.apache.http.client.methods.HttpGet; @@ -11,62 +52,66 @@ import org.apache.http.entity.mime.HttpMultipartMode; import org.apache.http.entity.mime.MultipartEntity; import org.apache.http.entity.mime.content.StringBody; import org.apache.http.impl.client.BasicResponseHandler; -import org.apache.http.impl.client.DefaultHttpClient; import org.apache.http.message.BasicNameValuePair; -import org.junit.After; -import org.junit.Before; +import org.apache.http.util.EntityUtils; import org.junit.Test; -import java.io.IOException; -import java.util.ArrayList; -import java.util.Collections; -import java.util.List; -import java.util.Map; - -import static org.junit.Assert.assertEquals; +import fi.iki.elonen.NanoHTTPD; +import fi.iki.elonen.NanoHTTPD.Response.Status; /** - * @author Paul S. Hawke (paul.hawke@gmail.com) - * On: 5/19/13 at 5:36 PM + * @author Paul S. Hawke (paul.hawke@gmail.com) On: 5/19/13 at 5:36 PM */ public class GetAndPostIntegrationTest extends IntegrationTestBase<GetAndPostIntegrationTest.TestServer> { - @Test - public void testSimpleGetRequest() throws Exception { - testServer.response = "testSimpleGetRequest"; + public static class TestServer extends NanoHTTPD { - HttpGet httpget = new HttpGet("http://localhost:8192/"); - ResponseHandler<String> responseHandler = new BasicResponseHandler(); - String responseBody = httpclient.execute(httpget, responseHandler); + public String response; - assertEquals("GET:testSimpleGetRequest", responseBody); - } + public TestServer() { + super(8192); + } - @Test - public void testGetRequestWithParameters() throws Exception { - testServer.response = "testGetRequestWithParameters"; + @Override + public Response serve(String uri, Method method, Map<String, String> header, Map<String, String> parms, Map<String, String> files) { + StringBuilder sb = new StringBuilder(String.valueOf(method) + ':' + this.response); - HttpGet httpget = new HttpGet("http://localhost:8192/?age=120&gender=Male"); - ResponseHandler<String> responseHandler = new BasicResponseHandler(); - String responseBody = httpclient.execute(httpget, responseHandler); + if (parms.size() > 1) { + parms.remove("NanoHttpd.QUERY_STRING"); + sb.append("-params=").append(parms.size()); + List<String> p = new ArrayList<String>(parms.keySet()); + Collections.sort(p); + for (String k : p) { + sb.append(';').append(k).append('=').append(parms.get(k)); + } + } + if ("/chin".equals(uri)) { + return newFixedLengthResponse(Status.OK, "application/octet-stream", sb.toString()); + } else { + return newFixedLengthResponse(sb.toString()); + } + } + } - assertEquals("GET:testGetRequestWithParameters-params=2;age=120;gender=Male", responseBody); + @Override + public TestServer createTestServer() { + return new TestServer(); } @Test - public void testPostWithNoParameters() throws Exception { - testServer.response = "testPostWithNoParameters"; + public void testGetRequestWithParameters() throws Exception { + this.testServer.response = "testGetRequestWithParameters"; - HttpPost httppost = new HttpPost("http://localhost:8192/"); + HttpGet httpget = new HttpGet("http://localhost:8192/?age=120&gender=Male"); ResponseHandler<String> responseHandler = new BasicResponseHandler(); - String responseBody = httpclient.execute(httppost, responseHandler); + String responseBody = this.httpclient.execute(httpget, responseHandler); - assertEquals("POST:testPostWithNoParameters", responseBody); + assertEquals("GET:testGetRequestWithParameters-params=2;age=120;gender=Male", responseBody); } @Test public void testPostRequestWithFormEncodedParameters() throws Exception { - testServer.response = "testPostRequestWithFormEncodedParameters"; + this.testServer.response = "testPostRequestWithFormEncodedParameters"; HttpPost httppost = new HttpPost("http://localhost:8192/"); List<NameValuePair> postParameters = new ArrayList<NameValuePair>(); @@ -75,14 +120,14 @@ public class GetAndPostIntegrationTest extends IntegrationTestBase<GetAndPostInt httppost.setEntity(new UrlEncodedFormEntity(postParameters)); ResponseHandler<String> responseHandler = new BasicResponseHandler(); - String responseBody = httpclient.execute(httppost, responseHandler); + String responseBody = this.httpclient.execute(httppost, responseHandler); assertEquals("POST:testPostRequestWithFormEncodedParameters-params=2;age=120;gender=Male", responseBody); } @Test public void testPostRequestWithMultipartEncodedParameters() throws Exception { - testServer.response = "testPostRequestWithMultipartEncodedParameters"; + this.testServer.response = "testPostRequestWithMultipartEncodedParameters"; HttpPost httppost = new HttpPost("http://localhost:8192/"); MultipartEntity reqEntity = new MultipartEntity(HttpMultipartMode.BROWSER_COMPATIBLE); @@ -91,37 +136,53 @@ public class GetAndPostIntegrationTest extends IntegrationTestBase<GetAndPostInt httppost.setEntity(reqEntity); ResponseHandler<String> responseHandler = new BasicResponseHandler(); - String responseBody = httpclient.execute(httppost, responseHandler); + String responseBody = this.httpclient.execute(httppost, responseHandler); assertEquals("POST:testPostRequestWithMultipartEncodedParameters-params=2;age=120;gender=Male", responseBody); } - @Override public TestServer createTestServer() { - return new TestServer(); + @Test + public void testPostWithNoParameters() throws Exception { + this.testServer.response = "testPostWithNoParameters"; + + HttpPost httppost = new HttpPost("http://localhost:8192/"); + ResponseHandler<String> responseHandler = new BasicResponseHandler(); + String responseBody = this.httpclient.execute(httppost, responseHandler); + + assertEquals("POST:testPostWithNoParameters", responseBody); } - public static class TestServer extends NanoHTTPD { - public String response; + @Test + public void testSimpleGetRequest() throws Exception { + this.testServer.response = "testSimpleGetRequest"; - public TestServer() { - super(8192); - } + HttpGet httpget = new HttpGet("http://localhost:8192/"); + ResponseHandler<String> responseHandler = new BasicResponseHandler(); + String responseBody = this.httpclient.execute(httpget, responseHandler); - @Override - public Response serve(String uri, Method method, Map<String, String> header, Map<String, String> parms, Map<String, String> files) { - StringBuilder sb = new StringBuilder(String.valueOf(method) + ':' + response); + assertEquals("GET:testSimpleGetRequest", responseBody); + } - if (parms.size() > 1) { - parms.remove("NanoHttpd.QUERY_STRING"); - sb.append("-params=").append(parms.size()); - List<String> p = new ArrayList<String>(parms.keySet()); - Collections.sort(p); - for (String k : p) { - sb.append(';').append(k).append('=').append(parms.get(k)); - } + @Test + public void testPostRequestWithMultipartExtremEncodedParameters() throws Exception { + this.testServer.response = "testPostRequestWithMultipartEncodedParameters"; + + HttpPost httppost = new HttpPost("http://localhost:8192/chin"); + MultipartEntity reqEntity = new MultipartEntity(HttpMultipartMode.BROWSER_COMPATIBLE, "sfsadfasdf", Charset.forName("UTF-8")); + reqEntity.addPart("specialString", new StringBody("拖拉图片到浏览器,可以实现预览功能", "text/plain", Charset.forName("UTF-8"))); + reqEntity.addPart("gender", new StringBody("图片名称", Charset.forName("UTF-8")) { + + @Override + public String getFilename() { + return "图片名称"; } + }); + httppost.setEntity(reqEntity); + HttpResponse response = this.httpclient.execute(httppost); - return new Response(sb.toString()); - } + HttpEntity entity = response.getEntity(); + String responseBody = EntityUtils.toString(entity, "UTF-8"); + + assertEquals("POST:testPostRequestWithMultipartEncodedParameters-params=2;gender=图片名称;specialString=拖拉图片到浏览器,可以实现预览功能", responseBody); } } diff --git a/core/src/test/java/fi/iki/elonen/integration/IntegrationTestBase.java b/core/src/test/java/fi/iki/elonen/integration/IntegrationTestBase.java index eb34033..fd3d6d3 100644 --- a/core/src/test/java/fi/iki/elonen/integration/IntegrationTestBase.java +++ b/core/src/test/java/fi/iki/elonen/integration/IntegrationTestBase.java @@ -1,27 +1,63 @@ package fi.iki.elonen.integration; -import fi.iki.elonen.NanoHTTPD; -import org.apache.http.client.HttpClient; +/* + * #%L + * NanoHttpd-Core + * %% + * Copyright (C) 2012 - 2015 nanohttpd + * %% + * Redistribution and use in source and binary forms, with or without modification, + * are permitted provided that the following conditions are met: + * + * 1. Redistributions of source code must retain the above copyright notice, this + * list of conditions and the following disclaimer. + * + * 2. Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * 3. Neither the name of the nanohttpd nor the names of its contributors + * may be used to endorse or promote products derived from this software without + * specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. + * IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, + * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, + * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF + * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE + * OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED + * OF THE POSSIBILITY OF SUCH DAMAGE. + * #L% + */ + +import java.io.IOException; + import org.apache.http.impl.client.DefaultHttpClient; import org.junit.After; import org.junit.Before; -import java.io.IOException; +import fi.iki.elonen.NanoHTTPD; /** - * @author Paul S. Hawke (paul.hawke@gmail.com) - * On: 9/2/13 at 10:02 PM + * @author Paul S. Hawke (paul.hawke@gmail.com) On: 9/2/13 at 10:02 PM */ public abstract class IntegrationTestBase<T extends NanoHTTPD> { + protected DefaultHttpClient httpclient; + protected T testServer; + public abstract T createTestServer(); + @Before public void setUp() { - testServer = createTestServer(); - httpclient = new DefaultHttpClient(); + this.testServer = createTestServer(); + this.httpclient = new DefaultHttpClient(); try { - testServer.start(); + this.testServer.start(); } catch (IOException e) { e.printStackTrace(); } @@ -29,9 +65,7 @@ public abstract class IntegrationTestBase<T extends NanoHTTPD> { @After public void tearDown() { - httpclient.getConnectionManager().shutdown(); - testServer.stop(); + this.httpclient.getConnectionManager().shutdown(); + this.testServer.stop(); } - - public abstract T createTestServer(); } diff --git a/core/src/test/java/fi/iki/elonen/integration/PutStreamIntegrationTest.java b/core/src/test/java/fi/iki/elonen/integration/PutStreamIntegrationTest.java index 1e260b2..41b84fd 100644 --- a/core/src/test/java/fi/iki/elonen/integration/PutStreamIntegrationTest.java +++ b/core/src/test/java/fi/iki/elonen/integration/PutStreamIntegrationTest.java @@ -1,5 +1,38 @@ package fi.iki.elonen.integration; +/* + * #%L + * NanoHttpd-Core + * %% + * Copyright (C) 2012 - 2015 nanohttpd + * %% + * Redistribution and use in source and binary forms, with or without modification, + * are permitted provided that the following conditions are met: + * + * 1. Redistributions of source code must retain the above copyright notice, this + * list of conditions and the following disclaimer. + * + * 2. Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * 3. Neither the name of the nanohttpd nor the names of its contributors + * may be used to endorse or promote products derived from this software without + * specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. + * IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, + * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, + * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF + * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE + * OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED + * OF THE POSSIBILITY OF SUCH DAMAGE. + * #L% + */ + import static org.junit.Assert.assertEquals; import java.io.DataInputStream; @@ -16,34 +49,13 @@ import fi.iki.elonen.NanoHTTPD; public class PutStreamIntegrationTest extends IntegrationTestBase<PutStreamIntegrationTest.TestServer> { - @Test - public void testSimplePutRequest() throws Exception { - String expected = "This HttpPut request has a content-length of 48."; - - HttpPut httpput = new HttpPut("http://localhost:8192/"); - httpput.setEntity(new ByteArrayEntity(expected.getBytes())); - ResponseHandler<String> responseHandler = new BasicResponseHandler(); - String responseBody = httpclient.execute(httpput, responseHandler); - - assertEquals("PUT:" + expected, responseBody); - } - - @Override public TestServer createTestServer() { - return new TestServer(); - } - public static class TestServer extends NanoHTTPD { + public TestServer() { super(8192); } @Override - public Response serve(String uri, Method method, Map<String, String> headers, Map<String, String> parms, Map<String, String> files) - { - throw new UnsupportedOperationException(); - } - - @Override public Response serve(IHTTPSession session) { Method method = session.getMethod(); Map<String, String> headers = session.getHeaders(); @@ -54,13 +66,34 @@ public class PutStreamIntegrationTest extends IntegrationTestBase<PutStreamInteg DataInputStream dataInputStream = new DataInputStream(session.getInputStream()); body = new byte[contentLength]; dataInputStream.readFully(body, 0, contentLength); - } - catch(IOException e) { - return new Response(Response.Status.INTERNAL_ERROR, MIME_PLAINTEXT, e.getMessage()); + } catch (IOException e) { + return newFixedLengthResponse(Response.Status.INTERNAL_ERROR, NanoHTTPD.MIME_PLAINTEXT, e.getMessage()); } String response = String.valueOf(method) + ':' + new String(body); - return new Response(response); + return newFixedLengthResponse(response); + } + + @Override + public Response serve(String uri, Method method, Map<String, String> headers, Map<String, String> parms, Map<String, String> files) { + throw new UnsupportedOperationException(); } } + + @Override + public TestServer createTestServer() { + return new TestServer(); + } + + @Test + public void testSimplePutRequest() throws Exception { + String expected = "This HttpPut request has a content-length of 48."; + + HttpPut httpput = new HttpPut("http://localhost:8192/"); + httpput.setEntity(new ByteArrayEntity(expected.getBytes())); + ResponseHandler<String> responseHandler = new BasicResponseHandler(); + String responseBody = this.httpclient.execute(httpput, responseHandler); + + assertEquals("PUT:" + expected, responseBody); + } } diff --git a/core/src/test/java/fi/iki/elonen/integration/ShutdownTest.java b/core/src/test/java/fi/iki/elonen/integration/ShutdownTest.java index 0fcb275..cd305ea 100644 --- a/core/src/test/java/fi/iki/elonen/integration/ShutdownTest.java +++ b/core/src/test/java/fi/iki/elonen/integration/ShutdownTest.java @@ -1,9 +1,39 @@ package fi.iki.elonen.integration; -import static org.junit.Assert.*; -import fi.iki.elonen.NanoHTTPD; +/* + * #%L + * NanoHttpd-Core + * %% + * Copyright (C) 2012 - 2015 nanohttpd + * %% + * Redistribution and use in source and binary forms, with or without modification, + * are permitted provided that the following conditions are met: + * + * 1. Redistributions of source code must retain the above copyright notice, this + * list of conditions and the following disclaimer. + * + * 2. Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * 3. Neither the name of the nanohttpd nor the names of its contributors + * may be used to endorse or promote products derived from this software without + * specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. + * IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, + * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, + * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF + * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE + * OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED + * OF THE POSSIBILITY OF SUCH DAMAGE. + * #L% + */ -import org.junit.Test; +import static org.junit.Assert.fail; import java.io.IOException; import java.io.InputStream; @@ -11,8 +41,24 @@ import java.net.HttpURLConnection; import java.net.MalformedURLException; import java.net.URL; +import org.junit.Test; + +import fi.iki.elonen.NanoHTTPD; + public class ShutdownTest { + private class TestServer extends NanoHTTPD { + + public TestServer() { + super(8092); + } + + @Override + public Response serve(IHTTPSession session) { + return newFixedLengthResponse("Whatever"); + } + } + @Test public void connectionsAreClosedWhenServerStops() throws IOException { TestServer server = new TestServer(); @@ -38,16 +84,4 @@ public class ShutdownTest { in.close(); } - private class TestServer extends NanoHTTPD { - - public TestServer() { - super(8092); - } - - @Override - public Response serve(IHTTPSession session) { - return new Response("Whatever"); - } - } - } |