You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@hc.apache.org by ol...@apache.org on 2020/04/20 17:39:16 UTC

[httpcomponents-core] 01/01: Improved integration test for out-of-sequence response handling by the HTTP/1.1 async protocol handler

This is an automated email from the ASF dual-hosted git repository.

olegk pushed a commit to branch development
in repository https://gitbox.apache.org/repos/asf/httpcomponents-core.git

commit 8c7f3de65ff0fde559c45d5d29db95618667f589
Author: Oleg Kalnichevski <ol...@apache.org>
AuthorDate: Mon Apr 20 19:38:38 2020 +0200

    Improved integration test for out-of-sequence response handling by the HTTP/1.1 async protocol handler
---
 .../hc/core5/testing/nio/Http1IntegrationTest.java | 21 +++++++++-
 ...tyProducer.java => MultiBinEntityProducer.java} | 46 +++++++++++++---------
 .../core5/testing/nio/MultiLineEntityProducer.java | 10 ++++-
 3 files changed, 56 insertions(+), 21 deletions(-)

diff --git a/httpcore5-testing/src/test/java/org/apache/hc/core5/testing/nio/Http1IntegrationTest.java b/httpcore5-testing/src/test/java/org/apache/hc/core5/testing/nio/Http1IntegrationTest.java
index ea990a0..67859d6 100644
--- a/httpcore5-testing/src/test/java/org/apache/hc/core5/testing/nio/Http1IntegrationTest.java
+++ b/httpcore5-testing/src/test/java/org/apache/hc/core5/testing/nio/Http1IntegrationTest.java
@@ -1034,9 +1034,26 @@ public class Http1IntegrationTest extends InternalHttp1ServerTestBase {
                 "localhost", serverEndpoint.getPort(), TIMEOUT);
         final ClientSessionEndpoint streamEndpoint = connectFuture.get();
 
+        for (int i = 0; i < 3; i++) {
+            final HttpRequest request1 = new BasicHttpRequest(Method.POST, createRequestURI(serverEndpoint, "/echo"));
+            final Future<Message<HttpResponse, String>> future1 = streamEndpoint.execute(
+                    new BasicRequestProducer(request1, new MultiLineEntityProducer("0123456789abcdef", 100000)),
+                    new BasicResponseConsumer<>(new StringAsyncEntityConsumer()), null);
+            final Message<HttpResponse, String> result1 = future1.get(TIMEOUT.getDuration(), TIMEOUT.getTimeUnit());
+            Assert.assertNotNull(result1);
+            final HttpResponse response1 = result1.getHead();
+            Assert.assertNotNull(response1);
+            Assert.assertEquals(HttpStatus.SC_UNAUTHORIZED, response1.getCode());
+            Assert.assertNotNull("You shall not pass", result1.getBody());
+
+            Assert.assertTrue(streamEndpoint.isOpen());
+        }
         final HttpRequest request1 = new BasicHttpRequest(Method.POST, createRequestURI(serverEndpoint, "/echo"));
         final Future<Message<HttpResponse, String>> future1 = streamEndpoint.execute(
-                new BasicRequestProducer(request1, new MultiLineEntityProducer("0123456789abcdef", 5000)),
+                new BasicRequestProducer(request1, new MultiBinEntityProducer(
+                        new byte[] {'0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'a', 'b', 'c', 'd', 'e', 'f'},
+                        100000,
+                        ContentType.TEXT_PLAIN)),
                 new BasicResponseConsumer<>(new StringAsyncEntityConsumer()), null);
         final Message<HttpResponse, String> result1 = future1.get(TIMEOUT.getDuration(), TIMEOUT.getTimeUnit());
         Assert.assertNotNull(result1);
@@ -1044,6 +1061,8 @@ public class Http1IntegrationTest extends InternalHttp1ServerTestBase {
         Assert.assertNotNull(response1);
         Assert.assertEquals(HttpStatus.SC_UNAUTHORIZED, response1.getCode());
         Assert.assertNotNull("You shall not pass", result1.getBody());
+
+        Assert.assertFalse(streamEndpoint.isOpen());
     }
 
     @Test
diff --git a/httpcore5-testing/src/test/java/org/apache/hc/core5/testing/nio/MultiLineEntityProducer.java b/httpcore5-testing/src/test/java/org/apache/hc/core5/testing/nio/MultiBinEntityProducer.java
similarity index 65%
copy from httpcore5-testing/src/test/java/org/apache/hc/core5/testing/nio/MultiLineEntityProducer.java
copy to httpcore5-testing/src/test/java/org/apache/hc/core5/testing/nio/MultiBinEntityProducer.java
index 0c0a2fd..9c5188a 100644
--- a/httpcore5-testing/src/test/java/org/apache/hc/core5/testing/nio/MultiLineEntityProducer.java
+++ b/httpcore5-testing/src/test/java/org/apache/hc/core5/testing/nio/MultiBinEntityProducer.java
@@ -27,25 +27,25 @@
 package org.apache.hc.core5.testing.nio;
 
 import java.io.IOException;
-import java.nio.CharBuffer;
+import java.nio.ByteBuffer;
 
 import org.apache.hc.core5.http.ContentType;
 import org.apache.hc.core5.http.nio.StreamChannel;
-import org.apache.hc.core5.http.nio.entity.AbstractCharAsyncEntityProducer;
+import org.apache.hc.core5.http.nio.entity.AbstractBinAsyncEntityProducer;
 
-public class MultiLineEntityProducer extends AbstractCharAsyncEntityProducer {
+public class MultiBinEntityProducer extends AbstractBinAsyncEntityProducer {
 
-    private final String text;
+    private final byte[] bin;
     private final int total;
-    private final CharBuffer charbuf;
+    private final ByteBuffer bytebuf;
 
     private int count;
 
-    public MultiLineEntityProducer(final String text, final int total) {
-        super(1024, -1, ContentType.TEXT_PLAIN);
-        this.text = text;
+    public MultiBinEntityProducer(final byte[] bin, final int total, final ContentType contentType) {
+        super(-1, contentType);
+        this.bin = bin;
         this.total = total;
-        this.charbuf = CharBuffer.allocate(4096);
+        this.bytebuf = ByteBuffer.allocate(4096);
         this.count = 0;
     }
 
@@ -60,29 +60,39 @@ public class MultiLineEntityProducer extends AbstractCharAsyncEntityProducer {
     }
 
     @Override
-    protected void produceData(final StreamChannel<CharBuffer> channel) throws IOException {
-        while (charbuf.remaining() > text.length() + 2 && count < total) {
-            charbuf.put(text + "\r\n");
+    protected void produceData(final StreamChannel<ByteBuffer> channel) throws IOException {
+        while (bytebuf.remaining() > bin.length + 2 && count < total) {
+            bytebuf.put(bin);
             count++;
         }
-        if (charbuf.position() > 0) {
-            charbuf.flip();
-            channel.write(charbuf);
-            charbuf.compact();
+        if (bytebuf.position() > 0) {
+            bytebuf.flip();
+            channel.write(bytebuf);
+            bytebuf.compact();
         }
-        if (count >= total && charbuf.position() == 0) {
+        if (count >= total && bytebuf.position() == 0) {
             channel.endStream();
         }
     }
 
     @Override
+    public boolean isChunked() {
+        return false;
+    }
+
+    @Override
+    public long getContentLength() {
+        return bin.length * total;
+    }
+
+    @Override
     public void failed(final Exception cause) {
     }
 
     @Override
     public void releaseResources() {
         count = 0;
-        charbuf.clear();
+        bytebuf.clear();
         super.releaseResources();
     }
 
diff --git a/httpcore5-testing/src/test/java/org/apache/hc/core5/testing/nio/MultiLineEntityProducer.java b/httpcore5-testing/src/test/java/org/apache/hc/core5/testing/nio/MultiLineEntityProducer.java
index 0c0a2fd..c0a24f5 100644
--- a/httpcore5-testing/src/test/java/org/apache/hc/core5/testing/nio/MultiLineEntityProducer.java
+++ b/httpcore5-testing/src/test/java/org/apache/hc/core5/testing/nio/MultiLineEntityProducer.java
@@ -28,6 +28,8 @@ package org.apache.hc.core5.testing.nio;
 
 import java.io.IOException;
 import java.nio.CharBuffer;
+import java.nio.charset.Charset;
+import java.nio.charset.StandardCharsets;
 
 import org.apache.hc.core5.http.ContentType;
 import org.apache.hc.core5.http.nio.StreamChannel;
@@ -41,14 +43,18 @@ public class MultiLineEntityProducer extends AbstractCharAsyncEntityProducer {
 
     private int count;
 
-    public MultiLineEntityProducer(final String text, final int total) {
-        super(1024, -1, ContentType.TEXT_PLAIN);
+    public MultiLineEntityProducer(final String text, final int total, final Charset charset) {
+        super(1024, -1, ContentType.TEXT_PLAIN.withCharset(charset));
         this.text = text;
         this.total = total;
         this.charbuf = CharBuffer.allocate(4096);
         this.count = 0;
     }
 
+    public MultiLineEntityProducer(final String text, final int total) {
+        this(text, total, StandardCharsets.US_ASCII);
+    }
+
     @Override
     public boolean isRepeatable() {
         return true;