Skip to content

Commit e2cb286

Browse files
simplified tests
1 parent 320e8d8 commit e2cb286

File tree

2 files changed

+32
-215
lines changed

2 files changed

+32
-215
lines changed

services/s3/src/it/java/software/amazon/awssdk/services/s3/presignedurl/AsyncPresignedUrlManagerIntegrationTest.java

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -14,10 +14,17 @@
1414
*/
1515
package software.amazon.awssdk.services.s3.presignedurl;
1616

17+
import org.junit.jupiter.api.BeforeAll;
1718
import software.amazon.awssdk.services.s3.S3AsyncClient;
1819

1920
public class AsyncPresignedUrlManagerIntegrationTest extends AsyncPresignedUrlManagerTestSuite {
2021

22+
@BeforeAll
23+
static void setUpIntegrationTest() {
24+
S3AsyncClient s3AsyncClient = s3AsyncClientBuilder().build();
25+
presignedUrlManager = s3AsyncClient.presignedUrlManager();
26+
}
27+
2128
@Override
2229
protected S3AsyncClient createS3AsyncClient() {
2330
return s3AsyncClientBuilder().build();

services/s3/src/it/java/software/amazon/awssdk/services/s3/presignedurl/AsyncPresignedUrlManagerTestSuite.java

Lines changed: 25 additions & 215 deletions
Original file line numberDiff line numberDiff line change
@@ -14,23 +14,22 @@
1414
*/
1515
package software.amazon.awssdk.services.s3.presignedurl;
1616

17+
import static org.apache.commons.lang3.RandomStringUtils.randomAscii;
1718
import static org.assertj.core.api.Assertions.assertThat;
18-
import static org.assertj.core.api.Assertions.assertThatThrownBy;
1919

2020
import java.net.URL;
21+
import java.nio.charset.StandardCharsets;
2122
import java.nio.file.Path;
2223
import java.time.Duration;
2324
import java.util.ArrayList;
2425
import java.util.List;
2526
import java.util.UUID;
2627
import java.util.concurrent.CompletableFuture;
27-
import java.util.concurrent.ExecutionException;
2828
import java.util.concurrent.TimeUnit;
2929
import java.util.stream.Stream;
3030

3131
import org.junit.jupiter.api.AfterAll;
3232
import org.junit.jupiter.api.BeforeAll;
33-
import org.junit.jupiter.api.BeforeEach;
3433
import org.junit.jupiter.api.Test;
3534
import org.junit.jupiter.api.io.TempDir;
3635
import org.junit.jupiter.params.ParameterizedTest;
@@ -40,16 +39,13 @@
4039
import software.amazon.awssdk.core.ResponseBytes;
4140
import software.amazon.awssdk.core.async.AsyncRequestBody;
4241
import software.amazon.awssdk.core.async.AsyncResponseTransformer;
43-
import software.amazon.awssdk.core.exception.SdkClientException;
4442
import software.amazon.awssdk.metrics.MetricCollection;
4543
import software.amazon.awssdk.metrics.MetricPublisher;
4644
import software.amazon.awssdk.services.s3.S3AsyncClient;
4745
import software.amazon.awssdk.services.s3.S3IntegrationTestBase;
4846
import software.amazon.awssdk.services.s3.model.DeleteObjectRequest;
4947
import software.amazon.awssdk.services.s3.model.GetObjectResponse;
50-
import software.amazon.awssdk.services.s3.model.NoSuchKeyException;
5148
import software.amazon.awssdk.services.s3.model.PutObjectRequest;
52-
import software.amazon.awssdk.services.s3.model.S3Exception;
5349
import software.amazon.awssdk.services.s3.presigner.S3Presigner;
5450
import software.amazon.awssdk.services.s3.presigner.model.PresignedGetObjectRequest;
5551
import software.amazon.awssdk.services.s3.presignedurl.model.PresignedUrlGetObjectRequest;
@@ -61,15 +57,14 @@
6157
*/
6258
public abstract class AsyncPresignedUrlManagerTestSuite extends S3IntegrationTestBase {
6359
protected static S3Presigner presigner;
64-
protected AsyncPresignedUrlManager presignedUrlManager;
60+
protected static AsyncPresignedUrlManager presignedUrlManager;
6561
protected static String testBucket;
6662

6763
@TempDir
6864
static Path temporaryFolder;
6965

7066
protected static String testGetObjectKey;
7167
protected static String testLargeObjectKey;
72-
protected static String testNonExistentKey;
7368
protected static String testObjectContent;
7469
protected static byte[] testLargeObjectContent;
7570

@@ -87,12 +82,8 @@ static void setUpTestSuite() throws Exception {
8782
createBucket(testBucket);
8883
testGetObjectKey = generateRandomObjectKey();
8984
testLargeObjectKey = generateRandomObjectKey() + "-large";
90-
testNonExistentKey = generateRandomObjectKey() + "-nonexistent";
9185
testObjectContent = "Hello AsyncPresignedUrlManager Integration Test";
92-
testLargeObjectContent = new byte[5 * 1024 * 1024];
93-
for (int i = 0; i < testLargeObjectContent.length; i++) {
94-
testLargeObjectContent[i] = (byte) (i % 256);
95-
}
86+
testLargeObjectContent = randomAscii(5 * 1024 * 1024).getBytes(StandardCharsets.UTF_8);
9687
S3TestUtils.putObject(AsyncPresignedUrlManagerTestSuite.class, s3, testBucket, testGetObjectKey, testObjectContent);
9788
s3Async.putObject(
9889
PutObjectRequest.builder()
@@ -114,10 +105,16 @@ static void setUpTestSuite() throws Exception {
114105
});
115106
}
116107

117-
@BeforeEach
118-
void setUpEach() {
119-
S3AsyncClient s3AsyncClient = createS3AsyncClient();
120-
presignedUrlManager = s3AsyncClient.presignedUrlManager();
108+
@AfterAll
109+
static void tearDownTestSuite() {
110+
try {
111+
S3TestUtils.runCleanupTasks(AsyncPresignedUrlManagerTestSuite.class);
112+
} catch (Exception e) {
113+
}
114+
if (presigner != null) {
115+
presigner.close();
116+
}
117+
cleanUpResources();
121118
}
122119

123120
@ParameterizedTest(name = "{0}")
@@ -152,31 +149,6 @@ void getObject_withValidPresignedUrl_savesContentToFile() throws Exception {
152149
assertThat(downloadFile).hasContent(testObjectContent);
153150
}
154151

155-
@Test
156-
void getObject_withConsumerBuilder_returnsContent() throws Exception {
157-
URL presignedUrl = createPresignedUrl(testGetObjectKey);
158-
159-
CompletableFuture<ResponseBytes<GetObjectResponse>> bytesFuture =
160-
presignedUrlManager.getObject(
161-
builder -> builder.presignedUrl(presignedUrl),
162-
AsyncResponseTransformer.toBytes());
163-
ResponseBytes<GetObjectResponse> bytesResponse = bytesFuture.get();
164-
165-
assertThat(bytesResponse).isNotNull();
166-
assertThat(bytesResponse.asUtf8String()).isEqualTo(testObjectContent);
167-
168-
Path downloadFile = temporaryFolder.resolve("consumer-builder-download-" + UUID.randomUUID() + ".txt");
169-
CompletableFuture<GetObjectResponse> fileFuture =
170-
presignedUrlManager.getObject(
171-
builder -> builder.presignedUrl(presignedUrl),
172-
AsyncResponseTransformer.toFile(downloadFile));
173-
GetObjectResponse fileResponse = fileFuture.get();
174-
175-
assertThat(fileResponse).isNotNull();
176-
assertThat(downloadFile).exists();
177-
assertThat(downloadFile).hasContent(testObjectContent);
178-
}
179-
180152
@ParameterizedTest(name = "{0}")
181153
@MethodSource("rangeTestData")
182154
void getObject_withRangeRequest_returnsSpecifiedRange(String testDescription,
@@ -191,55 +163,6 @@ void getObject_withRangeRequest_returnsSpecifiedRange(String testDescription,
191163
assertThat(response.asUtf8String()).isEqualTo(expectedContent);
192164
}
193165

194-
@ParameterizedTest(name = "{0}")
195-
@MethodSource("errorHandlingTestData")
196-
void getObject_withInvalidRequest_throwsExpectedException(String testDescription,
197-
String errorType,
198-
Class<? extends Exception> expectedExceptionType) throws Exception {
199-
200-
PresignedUrlGetObjectRequest request = createErrorRequest(errorType);
201-
CompletableFuture<ResponseBytes<GetObjectResponse>> future =
202-
presignedUrlManager.getObject(request, AsyncResponseTransformer.toBytes());
203-
204-
switch (errorType) {
205-
case "nonExistentKey":
206-
assertThatThrownBy(future::get)
207-
.isInstanceOf(ExecutionException.class)
208-
.satisfies(ex -> {
209-
Throwable cause = ex.getCause();
210-
assertThat(cause).satisfiesAnyOf(
211-
c -> assertThat(c).isInstanceOf(NoSuchKeyException.class),
212-
c -> assertThat(c).isInstanceOf(SdkClientException.class)
213-
);
214-
});
215-
break;
216-
case "invalidUrl":
217-
case "expiredUrl":
218-
assertThatThrownBy(future::get)
219-
.isInstanceOf(ExecutionException.class)
220-
.satisfies(ex -> {
221-
Throwable cause = ex.getCause();
222-
assertThat(cause).satisfiesAnyOf(
223-
c -> assertThat(c).isInstanceOf(S3Exception.class),
224-
c -> assertThat(c).isInstanceOf(SdkClientException.class)
225-
);
226-
});
227-
break;
228-
case "malformedUrl":
229-
assertThatThrownBy(future::get)
230-
.isInstanceOf(ExecutionException.class)
231-
.satisfies(ex -> {
232-
Throwable cause = ex.getCause();
233-
// Accept either IllegalArgumentException or network-related exceptions
234-
assertThat(cause).satisfiesAnyOf(
235-
c -> assertThat(c).isInstanceOf(IllegalArgumentException.class),
236-
c -> assertThat(c).isInstanceOf(SdkClientException.class)
237-
);
238-
});
239-
break;
240-
}
241-
}
242-
243166
@Test
244167
void getObject_withMultipleRangeRequestsConcurrently_returnsCorrectContent() throws Exception {
245168
String concurrentTestKey = uploadTestObject("concurrent-test", "0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZ");
@@ -271,49 +194,7 @@ void getObject_withMultipleRangeRequestsConcurrently_returnsCorrectContent() thr
271194
}
272195

273196
@Test
274-
void getObject_withLargeObjectRanges_returnsCorrectChunks() throws Exception {
275-
List<CompletableFuture<ResponseBytes<GetObjectResponse>>> futures = new ArrayList<>();
276-
int chunkSize = 1024 * 1024;
277-
278-
for (int i = 0; i < 4; i++) {
279-
int start = i * chunkSize;
280-
int end = start + chunkSize - 1;
281-
String range = String.format("bytes=%d-%d", start, end);
282-
futures.add(presignedUrlManager.getObject(
283-
createRequestForKey(testLargeObjectKey, range),
284-
AsyncResponseTransformer.toBytes()));
285-
}
286-
287-
CompletableFuture<Void> allFutures = CompletableFuture.allOf(
288-
futures.toArray(new CompletableFuture[0]));
289-
allFutures.get(60, TimeUnit.SECONDS);
290-
for (int i = 0; i < futures.size(); i++) {
291-
ResponseBytes<GetObjectResponse> response = futures.get(i).get();
292-
assertThat(response.asByteArray()).hasSize(chunkSize);
293-
byte[] chunk = response.asByteArray();
294-
int baseOffset = i * chunkSize;
295-
for (int j = 0; j < chunk.length; j++) {
296-
int expectedValue = (baseOffset + j) % 256;
297-
assertThat(chunk[j]).isEqualTo((byte) expectedValue);
298-
}
299-
}
300-
}
301-
302-
@Test
303-
void getObject_withLargeObjectToFile_savesCompleteContent() throws Exception {
304-
PresignedUrlGetObjectRequest request = createRequestForKey(testLargeObjectKey);
305-
Path downloadFile = temporaryFolder.resolve("large-download-" + UUID.randomUUID() + ".bin");
306-
CompletableFuture<GetObjectResponse> future =
307-
presignedUrlManager.getObject(request, downloadFile);
308-
GetObjectResponse response = future.get();
309-
310-
assertThat(response).isNotNull();
311-
assertThat(downloadFile).exists();
312-
assertThat(downloadFile.toFile().length()).isEqualTo(testLargeObjectContent.length);
313-
}
314-
315-
@Test
316-
void getObject_withClientMetrics_collectsMetrics() throws Exception {
197+
void getObject_withLargeObjectToFile_savesCompleteContentAndCollectsMetrics() throws Exception {
317198
List<MetricCollection> collectedMetrics = new ArrayList<>();
318199
MetricPublisher metricPublisher = new MetricPublisher() {
319200
@Override
@@ -324,43 +205,31 @@ public void publish(MetricCollection metricCollection) {
324205
public void close() {}
325206
};
326207

327-
try (S3AsyncClient clientWithMetrics = S3AsyncClient.builder()
208+
try (S3AsyncClient clientWithMetrics = s3AsyncClientBuilder()
328209
.overrideConfiguration(o -> o.addMetricPublisher(metricPublisher))
329210
.build()) {
330211

331212
AsyncPresignedUrlManager metricsManager = clientWithMetrics.presignedUrlManager();
332-
PresignedUrlGetObjectRequest request = createRequestForKey(testGetObjectKey);
333-
334-
CompletableFuture<ResponseBytes<GetObjectResponse>> future =
335-
metricsManager.getObject(request, AsyncResponseTransformer.toBytes());
336-
ResponseBytes<GetObjectResponse> response = future.get(30, TimeUnit.SECONDS);
213+
PresignedUrlGetObjectRequest request = createRequestForKey(testLargeObjectKey);
214+
Path downloadFile = temporaryFolder.resolve("large-download-with-metrics-" + UUID.randomUUID() + ".bin");
215+
216+
CompletableFuture<GetObjectResponse> future =
217+
metricsManager.getObject(request, downloadFile);
218+
GetObjectResponse response = future.get(60, TimeUnit.SECONDS);
337219

338220
assertThat(response).isNotNull();
221+
assertThat(downloadFile).exists();
222+
assertThat(downloadFile.toFile().length()).isEqualTo(testLargeObjectContent.length);
339223
assertThat(collectedMetrics).isNotEmpty();
340224
}
341225
}
342226

343-
@Test
344-
void getObject_withBuilderPattern_returnsContent() throws Exception {
345-
PresignedUrlGetObjectRequest request = PresignedUrlGetObjectRequest.builder()
346-
.presignedUrl(createPresignedUrl(testGetObjectKey))
347-
.build();
348-
349-
CompletableFuture<ResponseBytes<GetObjectResponse>> future =
350-
presignedUrlManager.getObject(request, AsyncResponseTransformer.toBytes());
351-
352-
ResponseBytes<GetObjectResponse> response = future.get();
353-
assertThat(response.asUtf8String()).isEqualTo(testObjectContent);
354-
}
355-
356227
static Stream<Arguments> basicFunctionalityTestData() {
357228
return Stream.of(
358229
Arguments.of("getObject_withValidUrl_returnsContent",
359230
testGetObjectKey, testObjectContent),
360231
Arguments.of("getObject_withValidLargeObjectUrl_returnsContent",
361-
testLargeObjectKey, null),
362-
Arguments.of("getObject_withBuilderPattern_returnsContent",
363-
testGetObjectKey, testObjectContent)
232+
testLargeObjectKey, null)
364233
);
365234
}
366235

@@ -378,32 +247,6 @@ static Stream<Arguments> rangeTestData() {
378247
);
379248
}
380249

381-
static Stream<Arguments> errorHandlingTestData() {
382-
return Stream.of(
383-
Arguments.of("getObject_withNonExistentKey_throwsNoSuchKeyException",
384-
"nonExistentKey", NoSuchKeyException.class),
385-
Arguments.of("getObject_withInvalidUrl_throwsS3Exception",
386-
"invalidUrl", S3Exception.class),
387-
Arguments.of("getObject_withExpiredUrl_throwsS3Exception",
388-
"expiredUrl", S3Exception.class),
389-
Arguments.of("getObject_withMalformedUrl_throwsIllegalArgumentException",
390-
"malformedUrl", IllegalArgumentException.class)
391-
);
392-
}
393-
394-
@AfterAll
395-
static void tearDownTestSuite() {
396-
try {
397-
S3TestUtils.runCleanupTasks(AsyncPresignedUrlManagerTestSuite.class);
398-
} catch (Exception e) {
399-
}
400-
401-
if (presigner != null) {
402-
presigner.close();
403-
}
404-
cleanUpResources();
405-
}
406-
407250
// Helper methods
408251
private static String generateRandomObjectKey() {
409252
return "async-presigned-url-manager-test-" + UUID.randomUUID();
@@ -429,39 +272,6 @@ private URL createPresignedUrl(String key) {
429272
return presignedRequest.url();
430273
}
431274

432-
private PresignedUrlGetObjectRequest createErrorRequest(String errorType) {
433-
switch (errorType) {
434-
case "nonExistentKey":
435-
return createRequestForKey(testNonExistentKey);
436-
case "invalidUrl":
437-
return createRequestForKey("invalid-key-that-does-not-exist-" + UUID.randomUUID());
438-
case "expiredUrl":
439-
PresignedGetObjectRequest expiredRequest = presigner.presignGetObject(r -> r
440-
.getObjectRequest(req -> req.bucket(testBucket).key(testGetObjectKey))
441-
.signatureDuration(Duration.ofSeconds(1))); // Minimum valid duration
442-
try {
443-
Thread.sleep(2000);
444-
} catch (InterruptedException e) {
445-
Thread.currentThread().interrupt();
446-
throw new RuntimeException("Interrupted while waiting for URL to expire", e);
447-
}
448-
449-
return PresignedUrlGetObjectRequest.builder()
450-
.presignedUrl(expiredRequest.url())
451-
.build();
452-
case "malformedUrl":
453-
try {
454-
return PresignedUrlGetObjectRequest.builder()
455-
.presignedUrl(new URL("http://invalid-hostname-that-does-not-exist"))
456-
.build();
457-
} catch (Exception e) {
458-
throw new RuntimeException(e);
459-
}
460-
default:
461-
throw new IllegalArgumentException("Unknown error type: " + errorType);
462-
}
463-
}
464-
465275
private String uploadTestObject(String keyPrefix, String content) {
466276
String key = keyPrefix + "-" + UUID.randomUUID();
467277
S3TestUtils.putObject(AsyncPresignedUrlManagerTestSuite.class, s3, testBucket, key, content);

0 commit comments

Comments
 (0)