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/07/23 11:09:11 UTC

[httpcomponents-core] branch master updated: HTTPCORE-638: SharedOutputBuffer must trigger DataStreamChannel#endStream() once (#204)

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

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


The following commit(s) were added to refs/heads/master by this push:
     new 41ff6a8  HTTPCORE-638: SharedOutputBuffer must trigger DataStreamChannel#endStream() once (#204)
41ff6a8 is described below

commit 41ff6a8f1f4d20e1233fdc3df543f921f41d856e
Author: malaysf <ma...@gmail.com>
AuthorDate: Thu Jul 23 04:09:03 2020 -0700

    HTTPCORE-638: SharedOutputBuffer must trigger DataStreamChannel#endStream() once (#204)
---
 .../core5/http/nio/support/classic/SharedOutputBuffer.java | 13 +++++++++++--
 .../http/nio/support/classic/TestSharedOutputBuffer.java   | 14 ++++++++++++++
 2 files changed, 25 insertions(+), 2 deletions(-)

diff --git a/httpcore5/src/main/java/org/apache/hc/core5/http/nio/support/classic/SharedOutputBuffer.java b/httpcore5/src/main/java/org/apache/hc/core5/http/nio/support/classic/SharedOutputBuffer.java
index ee494f4..bf25a9b 100644
--- a/httpcore5/src/main/java/org/apache/hc/core5/http/nio/support/classic/SharedOutputBuffer.java
+++ b/httpcore5/src/main/java/org/apache/hc/core5/http/nio/support/classic/SharedOutputBuffer.java
@@ -43,10 +43,12 @@ public final class SharedOutputBuffer extends AbstractSharedBuffer implements Co
 
     private volatile DataStreamChannel dataStreamChannel;
     private volatile boolean hasCapacity;
+    private volatile boolean endStreamPropagated;
 
     public SharedOutputBuffer(final ReentrantLock lock, final int initialBufferSize) {
         super(lock, initialBufferSize);
         this.hasCapacity = false;
+        this.endStreamPropagated = false;
     }
 
     public SharedOutputBuffer(final int bufferSize) {
@@ -63,7 +65,7 @@ public final class SharedOutputBuffer extends AbstractSharedBuffer implements Co
                 dataStreamChannel.write(buffer());
             }
             if (!buffer().hasRemaining() && endStream) {
-                dataStreamChannel.endStream();
+                propagateEndStream();
             }
             condition.signalAll();
         } finally {
@@ -135,7 +137,7 @@ public final class SharedOutputBuffer extends AbstractSharedBuffer implements Co
                     if (buffer().hasRemaining()) {
                         dataStreamChannel.requestOutput();
                     } else {
-                        dataStreamChannel.endStream();
+                        propagateEndStream();
                     }
                 }
             }
@@ -162,4 +164,11 @@ public final class SharedOutputBuffer extends AbstractSharedBuffer implements Co
         setInputMode();
     }
 
+    private void propagateEndStream() throws IOException {
+        if (!endStreamPropagated) {
+            dataStreamChannel.endStream();
+            endStreamPropagated = true;
+        }
+    }
+
 }
diff --git a/httpcore5/src/test/java/org/apache/hc/core5/http/nio/support/classic/TestSharedOutputBuffer.java b/httpcore5/src/test/java/org/apache/hc/core5/http/nio/support/classic/TestSharedOutputBuffer.java
index 428b14d..6858dc2 100644
--- a/httpcore5/src/test/java/org/apache/hc/core5/http/nio/support/classic/TestSharedOutputBuffer.java
+++ b/httpcore5/src/test/java/org/apache/hc/core5/http/nio/support/classic/TestSharedOutputBuffer.java
@@ -229,5 +229,19 @@ public class TestSharedOutputBuffer {
         }
     }
 
+    @Test
+    public void testEndStreamOnlyCalledOnce() throws IOException {
+
+        final DataStreamChannel channel = Mockito.mock(DataStreamChannel.class);
+        final SharedOutputBuffer outputBuffer = new SharedOutputBuffer(20);
+
+        outputBuffer.flush(channel);
+
+        outputBuffer.writeCompleted();
+        outputBuffer.flush(channel);
+
+        Mockito.verify(channel, Mockito.times(1)).endStream();
+    }
+
 }