Skip to content

Integrate identity chain into SDK client construction - #771

Merged
arandito merged 1 commit into
smithy-lang:developfrom
arandito:default-chain-integration
Aug 20, 2026
Merged

Integrate identity chain into SDK client construction#771
arandito merged 1 commit into
smithy-lang:developfrom
arandito:default-chain-integration

Conversation

@arandito

Copy link
Copy Markdown
Contributor

Description

This PR integrates the new IdentityChain into generated AWS clients. A new AwsIdentityIntegration builds the default chain into aws_credentials_identity_resolver at client setup.

The integration also pins the identity resolver in the config's deep-copy memo ({id(resolver): resolver}) so it's shared by reference. Every operation deep-copies the config to isolate per-call plugin mutations, which would otherwise duplicate the resolver on each call; pinning it keeps the chain built once per client and reused across every operation.

Important

This branch builds on top of #758. Only the latest commit is the change under review here. Every earlier commit belongs to #758.

By submitting this pull request, I confirm that you can use, modify, copy, and redistribute this contribution, under the terms of your choice.

profile_name = None
if config_context is not None:
config_file = await config_context.parsed_profiles()
profile_name = config_context.profile_name

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Flagging from #773 (comment):

Here the generated setup passes config_context.profile_name into IdentityChain.create(), but the context's profile_name is never None: it falls back to AWS_PROFILE, then "default". See

def _resolve_profile_name(
self, explicit_profile: str | None
) -> tuple[str, str | None]:
"""Determine the active profile name and where it came from.
Priority: explicit argument > AWS_PROFILE env var > "default"
:returns: Tuple of (profile_name, origin), where origin describes the
source for error messages and is None when the name was defaulted.
"""
if explicit_profile is not None:
return explicit_profile, "the profile argument"
env_profile = os.environ.get(_PROFILE_ENV_VAR)
if env_profile is not None:
return env_profile, _PROFILE_ENV_VAR
return _DEFAULT_PROFILE, None

But #773's environment provider defers whenever profile_name is not None, so once both PRs land, a user with only env credentials and no profile configured would still get the environment provider skipped.

We should update this PR to pass the profile only when it comes from the explicit argument.

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Added in c5498f2. Needed to improve how we track the profile source to avoid weak string comparisons. They now use ConfigSource.

Chose not to make profile a config field since it's not a request lifecycle setting. The profile name mainly influences config resolution so the resolution context is the proper layer for it.

Alan4506
Alan4506 previously approved these changes Aug 19, 2026

@alexgromero alexgromero left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM! 🚀

@arandito
arandito merged commit dce5fa7 into smithy-lang:develop Aug 20, 2026
8 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants