Skip to content

Commit e07b117

Browse files
committed
Restore per-request credential override in AwsExecutionContextBuilder
1 parent 437f380 commit e07b117

2 files changed

Lines changed: 63 additions & 1 deletion

File tree

core/aws-core/src/main/java/software/amazon/awssdk/awscore/internal/AwsExecutionContextBuilder.java

Lines changed: 24 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -31,6 +31,7 @@
3131
import software.amazon.awssdk.auth.credentials.AwsCredentials;
3232
import software.amazon.awssdk.auth.signer.AwsSignerExecutionAttribute;
3333
import software.amazon.awssdk.awscore.AwsExecutionAttribute;
34+
import software.amazon.awssdk.awscore.AwsRequestOverrideConfiguration;
3435
import software.amazon.awssdk.awscore.client.config.AwsClientOption;
3536
import software.amazon.awssdk.awscore.internal.authcontext.AuthorizationStrategy;
3637
import software.amazon.awssdk.awscore.internal.authcontext.AuthorizationStrategyFactory;
@@ -307,14 +308,36 @@ private static void putAuthSchemeResolutionAttributes(ExecutionAttributes execut
307308
// request preferred over client.
308309
Map<String, AuthScheme<?>> authSchemes = clientConfig.option(SdkClientOption.AUTH_SCHEMES);
309310

310-
IdentityProviders identityProviders = clientConfig.option(SdkClientOption.IDENTITY_PROVIDERS);
311+
IdentityProviders identityProviders = resolveIdentityProviders(originalRequest, clientConfig);
311312

312313
executionAttributes
313314
.putAttribute(SdkInternalExecutionAttribute.AUTH_SCHEME_RESOLVER, authSchemeProvider)
314315
.putAttribute(SdkInternalExecutionAttribute.AUTH_SCHEMES, authSchemes)
315316
.putAttribute(SdkInternalExecutionAttribute.IDENTITY_PROVIDERS, identityProviders);
316317
}
317318

319+
private static IdentityProviders resolveIdentityProviders(SdkRequest originalRequest,
320+
SdkClientConfiguration clientConfig) {
321+
IdentityProviders identityProviders = clientConfig.option(SdkClientOption.IDENTITY_PROVIDERS);
322+
323+
// identityProviders can be null, for new core with old client. In this case, even if AwsRequestOverrideConfiguration
324+
// has credentialsIdentityProvider set (because it is in new core), it is ok to not setup IDENTITY_PROVIDERS, as old
325+
// client won't have AUTH_SCHEME_PROVIDER/AUTH_SCHEMES set either, which are also needed for SRA logic.
326+
if (identityProviders == null) {
327+
return null;
328+
}
329+
330+
return originalRequest
331+
.overrideConfiguration()
332+
.filter(c -> c instanceof AwsRequestOverrideConfiguration)
333+
.map(c -> (AwsRequestOverrideConfiguration) c)
334+
.map(c -> identityProviders.copy(b -> {
335+
c.credentialsIdentityProvider().ifPresent(b::putIdentityProvider);
336+
c.tokenIdentityProvider().ifPresent(b::putIdentityProvider);
337+
}))
338+
.orElse(identityProviders);
339+
}
340+
318341
/**
319342
* Finalize {@link SdkRequest} by running beforeExecution and modifyRequest interceptors.
320343
*

core/aws-core/src/test/java/software/amazon/awssdk/awscore/internal/AwsExecutionContextBuilderTest.java

Lines changed: 39 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -581,6 +581,45 @@ public void invokeInterceptorsAndCreateExecutionContext_noAuthSchemeProviderRequ
581581
assertThat(actualProvider).isSameAs(clientAuthSchemeProvider);
582582
}
583583

584+
/**
585+
* Per-request credential override via AwsRequestOverrideConfiguration.credentialsProvider() must be
586+
* reflected in IDENTITY_PROVIDERS even when AUTH_SCHEME_OPTIONS_RESOLVER is not set (old service client).
587+
*/
588+
@Test
589+
public void postSra_requestCredentialOverride_withoutAuthSchemeOptionsResolver_identityProvidersHasOverride() {
590+
IdentityProvider<AwsCredentialsIdentity> requestCredsProvider =
591+
StaticCredentialsProvider.create(AwsBasicCredentials.create("request-akid", "request-skid"));
592+
593+
SdkRequest request = NoopTestAwsRequest.builder()
594+
.overrideConfiguration(AwsRequestOverrideConfiguration.builder()
595+
.credentialsProvider(requestCredsProvider)
596+
.build())
597+
.build();
598+
599+
IdentityProviders clientIdentityProviders = IdentityProviders.builder()
600+
.putIdentityProvider(defaultCredentialsProvider)
601+
.build();
602+
603+
SdkClientConfiguration clientConfig = testClientConfiguration()
604+
.option(SdkClientOption.IDENTITY_PROVIDERS, clientIdentityProviders)
605+
.option(SdkClientOption.EXECUTION_INTERCEPTORS, Collections.emptyList())
606+
.build();
607+
608+
// No AUTH_SCHEME_OPTIONS_RESOLVER set — simulates old service client
609+
ClientExecutionParams<SdkRequest, SdkResponse> executionParams = clientExecutionParams(request);
610+
611+
ExecutionContext executionContext =
612+
AwsExecutionContextBuilder.invokeInterceptorsAndCreateExecutionContext(executionParams, clientConfig);
613+
614+
IdentityProviders resolvedProviders =
615+
executionContext.executionAttributes().getAttribute(SdkInternalExecutionAttribute.IDENTITY_PROVIDERS);
616+
617+
// The per-request credential override must be reflected in IDENTITY_PROVIDERS
618+
IdentityProvider<AwsCredentialsIdentity> resolvedCredProvider =
619+
resolvedProviders.identityProvider(AwsCredentialsIdentity.class);
620+
assertThat(resolvedCredProvider).isSameAs(requestCredsProvider);
621+
}
622+
584623
private ClientExecutionParams<SdkRequest, SdkResponse> clientExecutionParams() {
585624
return clientExecutionParams(sdkRequest);
586625
}

0 commit comments

Comments
 (0)