|
15 | 15 |
|
16 | 16 | package software.amazon.awssdk.services.s3.internal.crossregion;
|
17 | 17 |
|
| 18 | +import static org.assertj.core.api.Assertions.as; |
18 | 19 | import static org.assertj.core.api.Assertions.assertThat;
|
| 20 | +import static org.mockito.Mockito.verify; |
19 | 21 | import static software.amazon.awssdk.services.s3.internal.crossregion.S3CrossRegionAsyncClientTest.customHttpResponse;
|
20 | 22 | import static software.amazon.awssdk.services.s3.internal.crossregion.S3CrossRegionAsyncClientTest.successHttpResponse;
|
21 | 23 | import static software.amazon.awssdk.services.s3.internal.crossregion.S3DecoratorRedirectBaseTest.CROSS_REGION;
|
|
27 | 29 | import java.util.List;
|
28 | 30 | import java.util.function.Consumer;
|
29 | 31 | import java.util.function.Supplier;
|
| 32 | +import java.util.stream.Collectors; |
30 | 33 | import java.util.stream.Stream;
|
31 | 34 | import org.junit.jupiter.api.BeforeEach;
|
32 | 35 | import org.junit.jupiter.api.Test;
|
33 | 36 | import org.junit.jupiter.params.ParameterizedTest;
|
34 | 37 | import org.junit.jupiter.params.provider.Arguments;
|
35 | 38 | import org.junit.jupiter.params.provider.MethodSource;
|
| 39 | +import org.mockito.ArgumentCaptor; |
36 | 40 | import software.amazon.awssdk.core.interceptor.Context;
|
37 | 41 | import software.amazon.awssdk.core.interceptor.ExecutionAttributes;
|
38 | 42 | import software.amazon.awssdk.core.interceptor.ExecutionInterceptor;
|
39 | 43 | import software.amazon.awssdk.core.interceptor.SdkInternalExecutionAttribute;
|
40 | 44 | import software.amazon.awssdk.endpoints.EndpointProvider;
|
41 | 45 | import software.amazon.awssdk.http.AbortableInputStream;
|
| 46 | +import software.amazon.awssdk.http.HttpExecuteRequest; |
42 | 47 | import software.amazon.awssdk.http.HttpExecuteResponse;
|
| 48 | +import software.amazon.awssdk.http.SdkHttpMethod; |
| 49 | +import software.amazon.awssdk.http.SdkHttpRequest; |
43 | 50 | import software.amazon.awssdk.http.SdkHttpResponse;
|
| 51 | +import software.amazon.awssdk.regions.Region; |
44 | 52 | import software.amazon.awssdk.services.s3.S3Client;
|
45 | 53 | import software.amazon.awssdk.services.s3.S3ClientBuilder;
|
46 | 54 | import software.amazon.awssdk.services.s3.endpoints.S3EndpointProvider;
|
@@ -129,10 +137,89 @@ void crossRegionClient_createdWithWrapping_SuccessfullyIntercepts(Consumer<MockS
|
129 | 137 | assertThat(captureInterceptor.endpointProvider).isInstanceOf(endpointProviderType);
|
130 | 138 | }
|
131 | 139 |
|
| 140 | + |
| 141 | + @Test |
| 142 | + void crossRegionClient_CallsHeadObject_when_regionNameNotPresentInFallBackCall() { |
| 143 | + mockSyncHttpClient.stubResponses(customHttpResponse(301, null ), |
| 144 | + customHttpResponse(301, CROSS_REGION ), |
| 145 | + successHttpResponse(), successHttpResponse()); |
| 146 | + S3Client crossRegionClient = |
| 147 | + clientBuilder().endpointOverride(null).region(Region.US_WEST_2).serviceConfiguration(c -> c.crossRegionAccessEnabled(true)).build(); |
| 148 | + crossRegionClient.getObject(r -> r.bucket(BUCKET).key(KEY)); |
| 149 | + assertThat(captureInterceptor.endpointProvider).isInstanceOf(BucketEndpointProvider.class); |
| 150 | + |
| 151 | + List<SdkHttpRequest> requests = mockSyncHttpClient.getRequests(); |
| 152 | + assertThat(requests).hasSize(3); |
| 153 | + |
| 154 | + assertThat(requests.stream().map(req -> req.host().substring(10,req.host().length() - 14 )).collect(Collectors.toList())) |
| 155 | + .isEqualTo(Arrays.asList(Region.US_WEST_2.toString(), |
| 156 | + Region.US_WEST_2.toString(), |
| 157 | + CROSS_REGION)); |
| 158 | + |
| 159 | + assertThat(requests.stream().map(req -> req.method()).collect(Collectors.toList())) |
| 160 | + .isEqualTo(Arrays.asList(SdkHttpMethod.GET, |
| 161 | + SdkHttpMethod.HEAD, |
| 162 | + SdkHttpMethod.GET)); |
| 163 | + |
| 164 | + // Resetting the mock client to capture the new API request for second S3 Call. |
| 165 | + mockSyncHttpClient.reset(); |
| 166 | + mockSyncHttpClient.stubResponses(successHttpResponse(), successHttpResponse()); |
| 167 | + crossRegionClient.getObject(r -> r.bucket(BUCKET).key(KEY)); |
| 168 | + List<SdkHttpRequest> postCacheRequests = mockSyncHttpClient.getRequests(); |
| 169 | + |
| 170 | + assertThat(postCacheRequests.stream() |
| 171 | + .map(req -> req.host().substring(10,req.host().length() - 14 )) |
| 172 | + .collect(Collectors.toList())) |
| 173 | + .isEqualTo(Arrays.asList(CROSS_REGION)); |
| 174 | + assertThat(postCacheRequests.stream().map(req -> req.method()).collect(Collectors.toList())) |
| 175 | + .isEqualTo(Arrays.asList(SdkHttpMethod.GET)); |
| 176 | + assertThat(captureInterceptor.endpointProvider).isInstanceOf(BucketEndpointProvider.class); |
| 177 | + |
| 178 | + } |
| 179 | + |
| 180 | + |
| 181 | + @Test |
| 182 | + void crossRegionClient_CallsHeadObjectErrors_shouldTeminateTheAPI() { |
| 183 | + mockSyncHttpClient.stubResponses(customHttpResponse(301, null ), |
| 184 | + customHttpResponse(301, CROSS_REGION ), |
| 185 | + successHttpResponse(), successHttpResponse()); |
| 186 | + S3Client crossRegionClient = |
| 187 | + clientBuilder().endpointOverride(null).region(Region.US_WEST_2).serviceConfiguration(c -> c.crossRegionAccessEnabled(true)).build(); |
| 188 | + crossRegionClient.getObject(r -> r.bucket(BUCKET).key(KEY)); |
| 189 | + assertThat(captureInterceptor.endpointProvider).isInstanceOf(BucketEndpointProvider.class); |
| 190 | + |
| 191 | + List<SdkHttpRequest> requests = mockSyncHttpClient.getRequests(); |
| 192 | + assertThat(requests).hasSize(3); |
| 193 | + |
| 194 | + assertThat(requests.stream().map(req -> req.host().substring(10,req.host().length() - 14 )).collect(Collectors.toList())) |
| 195 | + .isEqualTo(Arrays.asList(Region.US_WEST_2.toString(), |
| 196 | + Region.US_WEST_2.toString(), |
| 197 | + CROSS_REGION)); |
| 198 | + |
| 199 | + assertThat(requests.stream().map(req -> req.method()).collect(Collectors.toList())) |
| 200 | + .isEqualTo(Arrays.asList(SdkHttpMethod.GET, |
| 201 | + SdkHttpMethod.HEAD, |
| 202 | + SdkHttpMethod.GET)); |
| 203 | + |
| 204 | + // Resetting the mock client to capture the new API request for second S3 Call. |
| 205 | + mockSyncHttpClient.reset(); |
| 206 | + mockSyncHttpClient.stubResponses(successHttpResponse(), successHttpResponse()); |
| 207 | + crossRegionClient.getObject(r -> r.bucket(BUCKET).key(KEY)); |
| 208 | + List<SdkHttpRequest> postCacheRequests = mockSyncHttpClient.getRequests(); |
| 209 | + |
| 210 | + assertThat(postCacheRequests.stream() |
| 211 | + .map(req -> req.host().substring(10,req.host().length() - 14 )) |
| 212 | + .collect(Collectors.toList())) |
| 213 | + .isEqualTo(Arrays.asList(CROSS_REGION)); |
| 214 | + assertThat(postCacheRequests.stream().map(req -> req.method()).collect(Collectors.toList())) |
| 215 | + .isEqualTo(Arrays.asList(SdkHttpMethod.GET)); |
| 216 | + assertThat(captureInterceptor.endpointProvider).isInstanceOf(BucketEndpointProvider.class); |
| 217 | + |
| 218 | + } |
| 219 | + |
132 | 220 | private S3ClientBuilder clientBuilder() {
|
133 | 221 | return S3Client.builder()
|
134 | 222 | .httpClient(mockSyncHttpClient)
|
135 |
| - .endpointOverride(URI.create("http://localhost")) |
136 | 223 | .overrideConfiguration(c -> c.addExecutionInterceptor(captureInterceptor));
|
137 | 224 | }
|
138 | 225 |
|
|
0 commit comments