AI-narrated article. Prose is preserved with pronunciation adjustments; code and image cues refer to the written article.
GitHub Actions OIDC: Test Who Can Assume Your AWS Role
This is the AI-narrated article. The prose follows the written post; pronunciation is adjusted, and code and images are announced separately.
Remove long-lived AWS keys, then test the permission boundary.
TL;DR: GitHub Actions OIDC replaces stored AWS keys with temporary credentials, but secure deployment still requires narrow token permissions, precise role trust, protected environments, and scoped resource access. This article follows the identity through those gates and illustrates a job-permission sketch and an exact audience-and-subject condition. The examples are configuration fragments, not a complete AWS deployment or a production validation.
A keyless workflow can still have a large blast radius
Your deployment job has no saved AWS access key. It exchanges a GitHub identity token for temporary credentials. That is a useful improvement—but the role still trusts every repository in the organisation, and its permissions cover every production bucket.
The credential lifetime improved. The authorisation boundary did not.
OIDC makes the caller's identity available to AWS. You must decide which identities may assume a role, which jobs may request tokens, and which operations that role may perform. This article connects those decisions to an illustrative job-permission sketch and a role-trust condition.
The examples illustrate permission and trust boundaries. They do not execute a deployment or certify a production policy.
Follow the identity through four gates
A GitHub job requests an OIDC token. AWS validates that token and evaluates the role's trust policy. If assumption succeeds, the role's effective permissions govern resource access. A protected deployment environment adds a separate gate before the job proceeds.
Image. Four gates from workflow job to resource access
GitHub's OIDC reference explains that id-token: write permits requesting an identity token. It does not grant write access to AWS. Likewise, contents: read concerns the GitHub token, rather than an S3 bucket.
Set permissions at the deployment job, rather than granting every job identity-token access. This configuration fragment illustrates the intent:
Code example. Refer to the written article for the complete code.
This is a permissions sketch, not an AWS deployment. With explicit permissions, unspecified GitHub token permissions become none; see workflow syntax. A job can still hold other credentials or execute code, so this setting does not sandbox its filesystem or network.
Review any action that receives credentials. GitHub's secure-use guidance recommends verified full commit SHA references. An immutable reference makes the reviewed code repeatable; source review remains necessary.
Make the trust condition identify the intended job
For a normal AWS audience, require sts.amazonaws.com. Require the exact approved subject as well. An illustrative condition block is:
Code example. Refer to the written article for the complete code.
This is only the Condition fragment. A complete role trust policy also specifies the configured OIDC provider principal and the AssumeRoleWithWebIdentity action. Follow GitHub's AWS configuration guide for that integration.
The subject above uses illustrative immutable owner and repository identifiers. GitHub documents both legacy name-based subjects and immutable-ID subjects; custom templates can change the shape again. Inspect the subject issued for your repository and context before copying a condition. Do not assume the example string matches your token.
When a job references an environment, that environment appears in its default subject instead of a branch or pull-request suffix. Consequently, trusting the production environment subject does not itself restrict which branches may deploy. Configure deployment branch/tag rules and appropriate review controls on the environment. Environment documentation also explains plan restrictions and that one listed required reviewer can approve.
AWS checks for a GitHub subject condition that is not null or solely wildcard characters. That validation still permits patterns broader than your intended caller. AWS's OIDC role guide recommends narrowing repository and branch scope.
Questions worth asking during review
Does OIDC eliminate every credential risk? It avoids storing a long-lived AWS key for this federation path. A compromised authorised job can still use the temporary credentials it receives.
Does a production environment subject prove the branch was approved? No. Check environment branch/tag restrictions and review controls. A job allowed to use that environment can carry its environment subject.