From 4be2e5fb0ba87586a798e9a1924e83fbb1260f9e Mon Sep 17 00:00:00 2001 From: Nikita Sokolov Date: Thu, 3 Aug 2023 10:53:40 +0400 Subject: [PATCH 1/3] InputStream#readAllBytes() should receive no premature EOS A read-call with len == 0 happens here: https://github.com/AdoptOpenJDK/openjdk-jdk11/blob/master/src/java.base/share/classes/java/io/InputStream.java#L396 --- .../amazon/awssdk/utils/async/InputStreamSubscriber.java | 3 +++ 1 file changed, 3 insertions(+) diff --git a/utils/src/main/java/software/amazon/awssdk/utils/async/InputStreamSubscriber.java b/utils/src/main/java/software/amazon/awssdk/utils/async/InputStreamSubscriber.java index 3098724907c1..081dc64fe911 100644 --- a/utils/src/main/java/software/amazon/awssdk/utils/async/InputStreamSubscriber.java +++ b/utils/src/main/java/software/amazon/awssdk/utils/async/InputStreamSubscriber.java @@ -102,6 +102,9 @@ public int read(byte[] b) { @Override public int read(byte[] bytes, int off, int len) { + if (len == 0) { + return 0; + } ByteBuffer byteBuffer = ByteBuffer.wrap(bytes, off, len); TransferResult transferResult = delegate.blockingTransferTo(byteBuffer); int dataTransferred = byteBuffer.position() - off; From d130b2b612c208439682aae5408dbfd5da8ffc87 Mon Sep 17 00:00:00 2001 From: Dongie Agnir Date: Thu, 7 Sep 2023 15:26:42 -0700 Subject: [PATCH 2/3] Add/Fix tests Fixed some of the tests since the assertions fail if the read length is 0. This is in line with the default implementation of `read(byte[],int,int)` in `InputStream`: https://github.com/openjdk/jdk11u/blob/d77215acdd6b9008d7f58c7ad5a82d6087c20f86/src/java.base/share/classes/java/io/InputStream.java#L267 --- .../utils/async/InputStreamSubscriber.java | 1 + .../async/InputStreamSubscriberTest.java | 19 +++++++++++++------ 2 files changed, 14 insertions(+), 6 deletions(-) diff --git a/utils/src/main/java/software/amazon/awssdk/utils/async/InputStreamSubscriber.java b/utils/src/main/java/software/amazon/awssdk/utils/async/InputStreamSubscriber.java index 081dc64fe911..8b88d27ddfe2 100644 --- a/utils/src/main/java/software/amazon/awssdk/utils/async/InputStreamSubscriber.java +++ b/utils/src/main/java/software/amazon/awssdk/utils/async/InputStreamSubscriber.java @@ -105,6 +105,7 @@ public int read(byte[] bytes, int off, int len) { if (len == 0) { return 0; } + ByteBuffer byteBuffer = ByteBuffer.wrap(bytes, off, len); TransferResult transferResult = delegate.blockingTransferTo(byteBuffer); int dataTransferred = byteBuffer.position() - off; diff --git a/utils/src/test/java/software/amazon/awssdk/utils/async/InputStreamSubscriberTest.java b/utils/src/test/java/software/amazon/awssdk/utils/async/InputStreamSubscriberTest.java index 091b1bb8a9aa..393ee5592782 100644 --- a/utils/src/test/java/software/amazon/awssdk/utils/async/InputStreamSubscriberTest.java +++ b/utils/src/test/java/software/amazon/awssdk/utils/async/InputStreamSubscriberTest.java @@ -58,8 +58,8 @@ public void onComplete_returnsEndOfStream_onRead() { publisher.subscribe(subscriber); publisher.complete(); assertThat(subscriber.read()).isEqualTo(-1); - assertThat(subscriber.read(new byte[0])).isEqualTo(-1); - assertThat(subscriber.read(new byte[0], 0, 0)).isEqualTo(-1); + assertThat(subscriber.read(new byte[1])).isEqualTo(-1); + assertThat(subscriber.read(new byte[1], 0, 1)).isEqualTo(-1); } @Test @@ -69,8 +69,8 @@ public void onError_throws_onRead() { publisher.subscribe(subscriber); publisher.error(exception); assertThatThrownBy(() -> subscriber.read()).isEqualTo(exception); - assertThatThrownBy(() -> subscriber.read(new byte[0])).isEqualTo(exception); - assertThatThrownBy(() -> subscriber.read(new byte[0], 0, 0)).isEqualTo(exception); + assertThatThrownBy(() -> subscriber.read(new byte[1])).isEqualTo(exception); + assertThatThrownBy(() -> subscriber.read(new byte[1], 0, 1)).isEqualTo(exception); } @Test @@ -128,8 +128,15 @@ public void read_afterClose_fails() { publisher.subscribe(subscriber); subscriber.close(); assertThatThrownBy(() -> subscriber.read()).isInstanceOf(CancellationException.class); - assertThatThrownBy(() -> subscriber.read(new byte[0])).isInstanceOf(CancellationException.class); - assertThatThrownBy(() -> subscriber.read(new byte[0], 0, 0)).isInstanceOf(CancellationException.class); + assertThatThrownBy(() -> subscriber.read(new byte[1])).isInstanceOf(CancellationException.class); + assertThatThrownBy(() -> subscriber.read(new byte[1], 0, 1)).isInstanceOf(CancellationException.class); + } + + @Test + public void readByteArray_0Len_returns0() { + publisher.subscribe(subscriber); + + assertThat(subscriber.read(new byte[1], 0, 0)).isEqualTo(0); } public static List stochastic_methodCallsSeemThreadSafe_parameters() { From 39e0c4b1e65179d090ea46520ee38b9d7105981c Mon Sep 17 00:00:00 2001 From: Dongie Agnir Date: Tue, 12 Sep 2023 10:37:46 -0700 Subject: [PATCH 3/3] Add changelog entry --- .changes/next-release/bugfix-AWSSDKforJavav2-2984eeb.json | 6 ++++++ 1 file changed, 6 insertions(+) create mode 100644 .changes/next-release/bugfix-AWSSDKforJavav2-2984eeb.json diff --git a/.changes/next-release/bugfix-AWSSDKforJavav2-2984eeb.json b/.changes/next-release/bugfix-AWSSDKforJavav2-2984eeb.json new file mode 100644 index 000000000000..859ddfff2d76 --- /dev/null +++ b/.changes/next-release/bugfix-AWSSDKforJavav2-2984eeb.json @@ -0,0 +1,6 @@ +{ + "type": "bugfix", + "category": "AWS SDK for Java v2", + "contributor": "faucct", + "description": "Fix `InputStreamSubscriber` to return 0 when reading a length of 0." +}