Search in sources :

Example 61 with HttpServlet

use of javax.servlet.http.HttpServlet in project jetty.project by eclipse.

the class AsyncIOTest method testSomeContentAvailableAfterServiceReturns.

@Test
public void testSomeContentAvailableAfterServiceReturns() throws Exception {
    final AtomicInteger count = new AtomicInteger();
    start(new HttpServlet() {

        @Override
        protected void service(final HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
            final AsyncContext asyncContext = request.startAsync();
            asyncContext.setTimeout(0);
            request.getInputStream().setReadListener(new EmptyReadListener() {

                @Override
                public void onDataAvailable() throws IOException {
                    count.incrementAndGet();
                    ServletInputStream input = request.getInputStream();
                    while (input.isReady()) {
                        int read = input.read();
                        if (read < 0)
                            break;
                    }
                    if (input.isFinished())
                        asyncContext.complete();
                }
            });
        }
    });
    Session session = newClient(new Session.Listener.Adapter());
    HttpFields fields = new HttpFields();
    MetaData.Request metaData = newRequest("GET", fields);
    HeadersFrame frame = new HeadersFrame(metaData, null, false);
    final CountDownLatch latch = new CountDownLatch(1);
    FuturePromise<Stream> promise = new FuturePromise<>();
    session.newStream(frame, promise, new Stream.Listener.Adapter() {

        @Override
        public void onHeaders(Stream stream, HeadersFrame frame) {
            if (frame.isEndStream())
                latch.countDown();
        }
    });
    Stream stream = promise.get(5, TimeUnit.SECONDS);
    // Wait until service() returns.
    Thread.sleep(1000);
    stream.data(new DataFrame(stream.getId(), ByteBuffer.allocate(1), false), Callback.NOOP);
    // Wait until onDataAvailable() returns.
    Thread.sleep(1000);
    stream.data(new DataFrame(stream.getId(), ByteBuffer.allocate(1), true), Callback.NOOP);
    Assert.assertTrue(latch.await(5, TimeUnit.SECONDS));
    // Make sure onDataAvailable() has been called twice
    Assert.assertEquals(2, count.get());
}
Also used : ReadListener(javax.servlet.ReadListener) HttpServlet(javax.servlet.http.HttpServlet) FuturePromise(org.eclipse.jetty.util.FuturePromise) HttpServletResponse(javax.servlet.http.HttpServletResponse) AsyncContext(javax.servlet.AsyncContext) IOException(java.io.IOException) InterruptedIOException(java.io.InterruptedIOException) DataFrame(org.eclipse.jetty.http2.frames.DataFrame) CountDownLatch(java.util.concurrent.CountDownLatch) HeadersFrame(org.eclipse.jetty.http2.frames.HeadersFrame) HttpServletRequest(javax.servlet.http.HttpServletRequest) ServletException(javax.servlet.ServletException) ServletInputStream(javax.servlet.ServletInputStream) AtomicInteger(java.util.concurrent.atomic.AtomicInteger) MetaData(org.eclipse.jetty.http.MetaData) HttpFields(org.eclipse.jetty.http.HttpFields) ServletInputStream(javax.servlet.ServletInputStream) Stream(org.eclipse.jetty.http2.api.Stream) Session(org.eclipse.jetty.http2.api.Session) Test(org.junit.Test)

Example 62 with HttpServlet

use of javax.servlet.http.HttpServlet in project jetty.project by eclipse.

the class PushCacheFilterTest method testPush.

@Test
public void testPush() throws Exception {
    final String primaryResource = "/primary.html";
    final String secondaryResource = "/secondary.png";
    final byte[] secondaryData = "SECONDARY".getBytes("UTF-8");
    start(new HttpServlet() {

        @Override
        protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
            String requestURI = req.getRequestURI();
            ServletOutputStream output = resp.getOutputStream();
            if (requestURI.endsWith(primaryResource))
                output.print("<html><head></head><body>PRIMARY</body></html>");
            else if (requestURI.endsWith(secondaryResource))
                output.write(secondaryData);
        }
    });
    final Session session = newClient(new Session.Listener.Adapter());
    // Request for the primary and secondary resource to build the cache.
    final String referrerURI = newURI(primaryResource);
    HttpFields primaryFields = new HttpFields();
    MetaData.Request primaryRequest = newRequest("GET", primaryResource, primaryFields);
    final CountDownLatch warmupLatch = new CountDownLatch(1);
    session.newStream(new HeadersFrame(primaryRequest, null, true), new Promise.Adapter<>(), new Stream.Listener.Adapter() {

        @Override
        public void onData(Stream stream, DataFrame frame, Callback callback) {
            callback.succeeded();
            if (frame.isEndStream()) {
                // Request for the secondary resource.
                HttpFields secondaryFields = new HttpFields();
                secondaryFields.put(HttpHeader.REFERER, referrerURI);
                MetaData.Request secondaryRequest = newRequest("GET", secondaryResource, secondaryFields);
                session.newStream(new HeadersFrame(secondaryRequest, null, true), new Promise.Adapter<>(), new Stream.Listener.Adapter() {

                    @Override
                    public void onData(Stream stream, DataFrame frame, Callback callback) {
                        callback.succeeded();
                        warmupLatch.countDown();
                    }
                });
            }
        }
    });
    Assert.assertTrue(warmupLatch.await(5, TimeUnit.SECONDS));
    // Request again the primary resource, we should get the secondary resource pushed.
    primaryRequest = newRequest("GET", primaryResource, primaryFields);
    final CountDownLatch primaryResponseLatch = new CountDownLatch(2);
    final CountDownLatch pushLatch = new CountDownLatch(2);
    session.newStream(new HeadersFrame(primaryRequest, null, true), new Promise.Adapter<>(), new Stream.Listener.Adapter() {

        @Override
        public void onHeaders(Stream stream, HeadersFrame frame) {
            MetaData.Response response = (MetaData.Response) frame.getMetaData();
            if (response.getStatus() == HttpStatus.OK_200)
                primaryResponseLatch.countDown();
        }

        @Override
        public void onData(Stream stream, DataFrame frame, Callback callback) {
            callback.succeeded();
            if (frame.isEndStream())
                primaryResponseLatch.countDown();
        }

        @Override
        public Stream.Listener onPush(Stream stream, PushPromiseFrame frame) {
            return new Adapter() {

                @Override
                public void onHeaders(Stream stream, HeadersFrame frame) {
                    MetaData.Response response = (MetaData.Response) frame.getMetaData();
                    if (response.getStatus() == HttpStatus.OK_200)
                        pushLatch.countDown();
                }

                @Override
                public void onData(Stream stream, DataFrame frame, Callback callback) {
                    callback.succeeded();
                    if (frame.isEndStream())
                        pushLatch.countDown();
                }
            };
        }
    });
    Assert.assertTrue(pushLatch.await(5, TimeUnit.SECONDS));
    Assert.assertTrue(primaryResponseLatch.await(5, TimeUnit.SECONDS));
}
Also used : ServletOutputStream(javax.servlet.ServletOutputStream) HeadersFrame(org.eclipse.jetty.http2.frames.HeadersFrame) HttpServletRequest(javax.servlet.http.HttpServletRequest) ServletException(javax.servlet.ServletException) MetaData(org.eclipse.jetty.http.MetaData) HttpFields(org.eclipse.jetty.http.HttpFields) Stream(org.eclipse.jetty.http2.api.Stream) ServletOutputStream(javax.servlet.ServletOutputStream) HttpServlet(javax.servlet.http.HttpServlet) HttpServletRequest(javax.servlet.http.HttpServletRequest) HttpServletResponse(javax.servlet.http.HttpServletResponse) IOException(java.io.IOException) DataFrame(org.eclipse.jetty.http2.frames.DataFrame) CountDownLatch(java.util.concurrent.CountDownLatch) PushPromiseFrame(org.eclipse.jetty.http2.frames.PushPromiseFrame) HttpServletResponse(javax.servlet.http.HttpServletResponse) Promise(org.eclipse.jetty.util.Promise) Callback(org.eclipse.jetty.util.Callback) Session(org.eclipse.jetty.http2.api.Session) Test(org.junit.Test)

Example 63 with HttpServlet

use of javax.servlet.http.HttpServlet in project jetty.project by eclipse.

the class PushCacheFilterTest method testRecursivePush.

@Test
public void testRecursivePush() throws Exception {
    final String primaryResource = "/primary.html";
    final String secondaryResource1 = "/secondary1.css";
    final String secondaryResource2 = "/secondary2.js";
    final String tertiaryResource = "/tertiary.png";
    start(new HttpServlet() {

        @Override
        protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
            String requestURI = request.getRequestURI();
            final ServletOutputStream output = response.getOutputStream();
            if (requestURI.endsWith(primaryResource))
                output.print("<html><head></head><body>PRIMARY</body></html>");
            else if (requestURI.endsWith(secondaryResource1))
                output.print("body { background-image: url(\"" + tertiaryResource + "\"); }");
            else if (requestURI.endsWith(secondaryResource2))
                output.print("(function() { window.alert('HTTP/2'); })()");
            if (requestURI.endsWith(tertiaryResource))
                output.write("TERTIARY".getBytes(StandardCharsets.UTF_8));
        }
    });
    final Session session = newClient(new Session.Listener.Adapter());
    // Request for the primary, secondary and tertiary resource to build the cache.
    final String primaryURI = newURI(primaryResource);
    HttpFields primaryFields = new HttpFields();
    MetaData.Request primaryRequest = newRequest("GET", primaryResource, primaryFields);
    final CountDownLatch warmupLatch = new CountDownLatch(2);
    session.newStream(new HeadersFrame(primaryRequest, null, true), new Promise.Adapter<>(), new Stream.Listener.Adapter() {

        @Override
        public void onData(Stream stream, DataFrame frame, Callback callback) {
            callback.succeeded();
            if (frame.isEndStream()) {
                // Request for the secondary resources.
                String secondaryURI1 = newURI(secondaryResource1);
                HttpFields secondaryFields1 = new HttpFields();
                secondaryFields1.put(HttpHeader.REFERER, primaryURI);
                MetaData.Request secondaryRequest1 = newRequest("GET", secondaryResource1, secondaryFields1);
                session.newStream(new HeadersFrame(secondaryRequest1, null, true), new Promise.Adapter<>(), new Stream.Listener.Adapter() {

                    @Override
                    public void onData(Stream stream, DataFrame frame, Callback callback) {
                        callback.succeeded();
                        if (frame.isEndStream()) {
                            // Request for the tertiary resource.
                            HttpFields tertiaryFields = new HttpFields();
                            tertiaryFields.put(HttpHeader.REFERER, secondaryURI1);
                            MetaData.Request tertiaryRequest = newRequest("GET", tertiaryResource, tertiaryFields);
                            session.newStream(new HeadersFrame(tertiaryRequest, null, true), new Promise.Adapter<>(), new Adapter() {

                                @Override
                                public void onData(Stream stream, DataFrame frame, Callback callback) {
                                    callback.succeeded();
                                    if (frame.isEndStream())
                                        warmupLatch.countDown();
                                }
                            });
                        }
                    }
                });
                HttpFields secondaryFields2 = new HttpFields();
                secondaryFields2.put(HttpHeader.REFERER, primaryURI);
                MetaData.Request secondaryRequest2 = newRequest("GET", secondaryResource2, secondaryFields2);
                session.newStream(new HeadersFrame(secondaryRequest2, null, true), new Promise.Adapter<>(), new Stream.Listener.Adapter() {

                    @Override
                    public void onData(Stream stream, DataFrame frame, Callback callback) {
                        callback.succeeded();
                        if (frame.isEndStream())
                            warmupLatch.countDown();
                    }
                });
            }
        }
    });
    Assert.assertTrue(warmupLatch.await(5, TimeUnit.SECONDS));
    Thread.sleep(1000);
    // Request again the primary resource, we should get the secondary and tertiary resources pushed.
    primaryRequest = newRequest("GET", primaryResource, primaryFields);
    final CountDownLatch primaryResponseLatch = new CountDownLatch(1);
    final CountDownLatch primaryPushesLatch = new CountDownLatch(3);
    final CountDownLatch recursiveLatch = new CountDownLatch(1);
    session.newStream(new HeadersFrame(primaryRequest, null, true), new Promise.Adapter<>(), new Stream.Listener.Adapter() {

        @Override
        public void onData(Stream stream, DataFrame frame, Callback callback) {
            callback.succeeded();
            if (frame.isEndStream())
                primaryResponseLatch.countDown();
        }

        @Override
        public Stream.Listener onPush(Stream stream, PushPromiseFrame frame) {
            // The stream id of the PUSH_PROMISE must
            // always be a client stream and therefore odd.
            Assert.assertEquals(1, frame.getStreamId() & 1);
            return new Adapter() {

                @Override
                public void onData(Stream stream, DataFrame frame, Callback callback) {
                    callback.succeeded();
                    if (frame.isEndStream())
                        primaryPushesLatch.countDown();
                }

                @Override
                public Stream.Listener onPush(Stream stream, PushPromiseFrame frame) {
                    return new Adapter() {

                        @Override
                        public void onData(Stream stream, DataFrame frame, Callback callback) {
                            callback.succeeded();
                            if (frame.isEndStream())
                                recursiveLatch.countDown();
                        }
                    };
                }
            };
        }
    });
    Assert.assertTrue(primaryPushesLatch.await(5, TimeUnit.SECONDS));
    Assert.assertFalse(recursiveLatch.await(1, TimeUnit.SECONDS));
    Assert.assertTrue(primaryResponseLatch.await(5, TimeUnit.SECONDS));
    // Make sure that explicitly requesting a secondary resource, we get the tertiary pushed.
    CountDownLatch secondaryResponseLatch = new CountDownLatch(1);
    CountDownLatch secondaryPushLatch = new CountDownLatch(1);
    MetaData.Request secondaryRequest = newRequest("GET", secondaryResource1, new HttpFields());
    session.newStream(new HeadersFrame(secondaryRequest, null, true), new Promise.Adapter<>(), new Stream.Listener.Adapter() {

        @Override
        public void onData(Stream stream, DataFrame frame, Callback callback) {
            callback.succeeded();
            if (frame.isEndStream())
                secondaryResponseLatch.countDown();
        }

        @Override
        public Stream.Listener onPush(Stream stream, PushPromiseFrame frame) {
            return new Adapter() {

                @Override
                public void onData(Stream stream, DataFrame frame, Callback callback) {
                    callback.succeeded();
                    if (frame.isEndStream())
                        secondaryPushLatch.countDown();
                }
            };
        }
    });
    Assert.assertTrue(secondaryPushLatch.await(5, TimeUnit.SECONDS));
    Assert.assertTrue(secondaryResponseLatch.await(5, TimeUnit.SECONDS));
}
Also used : ServletOutputStream(javax.servlet.ServletOutputStream) HeadersFrame(org.eclipse.jetty.http2.frames.HeadersFrame) HttpServletRequest(javax.servlet.http.HttpServletRequest) ServletException(javax.servlet.ServletException) MetaData(org.eclipse.jetty.http.MetaData) HttpFields(org.eclipse.jetty.http.HttpFields) Stream(org.eclipse.jetty.http2.api.Stream) ServletOutputStream(javax.servlet.ServletOutputStream) HttpServlet(javax.servlet.http.HttpServlet) HttpServletRequest(javax.servlet.http.HttpServletRequest) HttpServletResponse(javax.servlet.http.HttpServletResponse) IOException(java.io.IOException) DataFrame(org.eclipse.jetty.http2.frames.DataFrame) CountDownLatch(java.util.concurrent.CountDownLatch) PushPromiseFrame(org.eclipse.jetty.http2.frames.PushPromiseFrame) Promise(org.eclipse.jetty.util.Promise) Callback(org.eclipse.jetty.util.Callback) Session(org.eclipse.jetty.http2.api.Session) Test(org.junit.Test)

Example 64 with HttpServlet

use of javax.servlet.http.HttpServlet in project jetty.project by eclipse.

the class PushCacheFilterTest method testSelfPush.

@Test
public void testSelfPush() throws Exception {
    // The test case is that of a login page, for example.
    // When the user sends the credentials to the login page,
    // the login may fail and redirect to the same login page,
    // perhaps with different query parameters.
    // In this case a request for the login page will push
    // the login page itself, which will generate the pushed
    // request for the login page, which will push the login
    // page itself, etc. which is not the desired behavior.
    final String primaryResource = "/login.html";
    start(new HttpServlet() {

        @Override
        protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
            ServletOutputStream output = response.getOutputStream();
            String credentials = request.getParameter("credentials");
            if (credentials == null) {
                output.print("<html><head></head><body>LOGIN</body></html>");
            } else if ("secret".equals(credentials)) {
                output.print("<html><head></head><body>OK</body></html>");
            } else {
                response.setStatus(HttpStatus.TEMPORARY_REDIRECT_307);
                response.setHeader(HttpHeader.LOCATION.asString(), primaryResource);
            }
        }
    });
    final String primaryURI = newURI(primaryResource);
    final Session session = newClient(new Session.Listener.Adapter());
    // Login with the wrong credentials, causing a redirect to self.
    HttpFields primaryFields = new HttpFields();
    MetaData.Request primaryRequest = newRequest("GET", primaryResource + "?credentials=wrong", primaryFields);
    final CountDownLatch warmupLatch = new CountDownLatch(1);
    session.newStream(new HeadersFrame(primaryRequest, null, true), new Promise.Adapter<>(), new Stream.Listener.Adapter() {

        @Override
        public void onHeaders(Stream stream, HeadersFrame frame) {
            if (frame.isEndStream()) {
                MetaData.Response response = (MetaData.Response) frame.getMetaData();
                if (response.getStatus() == HttpStatus.TEMPORARY_REDIRECT_307) {
                    // Follow the redirect.
                    String location = response.getFields().get(HttpHeader.LOCATION);
                    HttpFields redirectFields = new HttpFields();
                    redirectFields.put(HttpHeader.REFERER, primaryURI);
                    MetaData.Request redirectRequest = newRequest("GET", location, redirectFields);
                    session.newStream(new HeadersFrame(redirectRequest, null, true), new Promise.Adapter<>(), new Adapter() {

                        @Override
                        public void onData(Stream stream, DataFrame frame, Callback callback) {
                            callback.succeeded();
                            if (frame.isEndStream())
                                warmupLatch.countDown();
                        }
                    });
                }
            }
        }
    });
    Assert.assertTrue(warmupLatch.await(5, TimeUnit.SECONDS));
    Thread.sleep(1000);
    // Login with the right credentials, there must be no push.
    primaryRequest = newRequest("GET", primaryResource + "?credentials=secret", primaryFields);
    final CountDownLatch primaryResponseLatch = new CountDownLatch(1);
    final CountDownLatch pushLatch = new CountDownLatch(1);
    session.newStream(new HeadersFrame(primaryRequest, null, true), new Promise.Adapter<>(), new Stream.Listener.Adapter() {

        @Override
        public void onData(Stream stream, DataFrame frame, Callback callback) {
            callback.succeeded();
            if (frame.isEndStream())
                primaryResponseLatch.countDown();
        }

        @Override
        public Stream.Listener onPush(Stream stream, PushPromiseFrame frame) {
            pushLatch.countDown();
            return null;
        }
    });
    Assert.assertFalse(pushLatch.await(1, TimeUnit.SECONDS));
    Assert.assertTrue(primaryResponseLatch.await(5, TimeUnit.SECONDS));
}
Also used : ServletOutputStream(javax.servlet.ServletOutputStream) HeadersFrame(org.eclipse.jetty.http2.frames.HeadersFrame) HttpServletRequest(javax.servlet.http.HttpServletRequest) ServletException(javax.servlet.ServletException) MetaData(org.eclipse.jetty.http.MetaData) HttpFields(org.eclipse.jetty.http.HttpFields) Stream(org.eclipse.jetty.http2.api.Stream) ServletOutputStream(javax.servlet.ServletOutputStream) HttpServlet(javax.servlet.http.HttpServlet) HttpServletRequest(javax.servlet.http.HttpServletRequest) HttpServletResponse(javax.servlet.http.HttpServletResponse) IOException(java.io.IOException) DataFrame(org.eclipse.jetty.http2.frames.DataFrame) CountDownLatch(java.util.concurrent.CountDownLatch) PushPromiseFrame(org.eclipse.jetty.http2.frames.PushPromiseFrame) HttpServletResponse(javax.servlet.http.HttpServletResponse) Promise(org.eclipse.jetty.util.Promise) Callback(org.eclipse.jetty.util.Callback) Session(org.eclipse.jetty.http2.api.Session) Test(org.junit.Test)

Example 65 with HttpServlet

use of javax.servlet.http.HttpServlet in project jetty.project by eclipse.

the class ConcatServletTest method testConcatenation.

@Test
public void testConcatenation() throws Exception {
    String contextPath = "";
    ServletContextHandler context = new ServletContextHandler(server, contextPath);
    server.setHandler(context);
    String concatPath = "/concat";
    context.addServlet(ConcatServlet.class, concatPath);
    ServletHolder resourceServletHolder = new ServletHolder(new HttpServlet() {

        @Override
        protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
            String includedURI = (String) request.getAttribute(RequestDispatcher.INCLUDE_REQUEST_URI);
            response.getOutputStream().println(includedURI);
        }
    });
    context.addServlet(resourceServletHolder, "/resource/*");
    server.start();
    String resource1 = "/resource/one.js";
    String resource2 = "/resource/two.js";
    String uri = contextPath + concatPath + "?" + resource1 + "&" + resource2;
    String request = "" + "GET " + uri + " HTTP/1.1\r\n" + "Host: localhost\r\n" + "Connection: close\r\n" + "\r\n";
    String response = connector.getResponses(request);
    try (BufferedReader reader = new BufferedReader(new StringReader(response))) {
        while (true) {
            String line = reader.readLine();
            if (line == null)
                Assert.fail();
            if (line.trim().isEmpty())
                break;
        }
        Assert.assertEquals(resource1, reader.readLine());
        Assert.assertEquals(resource2, reader.readLine());
        Assert.assertNull(reader.readLine());
    }
}
Also used : HttpServletRequest(javax.servlet.http.HttpServletRequest) ServletException(javax.servlet.ServletException) ServletHolder(org.eclipse.jetty.servlet.ServletHolder) HttpServlet(javax.servlet.http.HttpServlet) BufferedReader(java.io.BufferedReader) StringReader(java.io.StringReader) HttpServletResponse(javax.servlet.http.HttpServletResponse) IOException(java.io.IOException) ServletContextHandler(org.eclipse.jetty.servlet.ServletContextHandler) Test(org.junit.Test)

Aggregations

HttpServlet (javax.servlet.http.HttpServlet)173 HttpServletRequest (javax.servlet.http.HttpServletRequest)152 HttpServletResponse (javax.servlet.http.HttpServletResponse)152 IOException (java.io.IOException)130 ServletException (javax.servlet.ServletException)128 Test (org.junit.Test)117 CountDownLatch (java.util.concurrent.CountDownLatch)68 ContentResponse (org.eclipse.jetty.client.api.ContentResponse)61 InterruptedIOException (java.io.InterruptedIOException)55 ServletOutputStream (javax.servlet.ServletOutputStream)36 AsyncContext (javax.servlet.AsyncContext)34 HttpFields (org.eclipse.jetty.http.HttpFields)32 MetaData (org.eclipse.jetty.http.MetaData)32 HeadersFrame (org.eclipse.jetty.http2.frames.HeadersFrame)32 ServletInputStream (javax.servlet.ServletInputStream)31 Session (org.eclipse.jetty.http2.api.Session)30 Stream (org.eclipse.jetty.http2.api.Stream)27 Response (org.eclipse.jetty.client.api.Response)26 HttpContentResponse (org.eclipse.jetty.client.HttpContentResponse)24 HashMap (java.util.HashMap)22