GitHub Actions does not need a permanent AWS access key to deploy infrastructure. A cleaner pattern is to let GitHub present an OpenID Connect token to AWS STS and assume a tightly scoped IAM role for the duration of the job.

The deployment path

GitHub push → GitHub Actions → OIDC token → AWS STS → IAM role → Terraform plan/apply

The important shift is that GitHub stores no long-lived AWS secret. AWS decides whether the token is trusted, then issues temporary credentials.

What actually needs to exist

The two failure modes worth checking first

1. The trust policy does not match GitHub's subject claim

OIDC failures are often not an AWS-permission problem at all. The token's subject must match the condition in the role trust policy. Inspect the actual repository identity format you are receiving instead of assuming a name-only subject string.

2. Terraform fails before AWS authentication matters

A pipeline can be perfectly configured for OIDC and still die on terraform fmt -check, validation, packaging, or backend initialization. Keep those steps explicit so you can identify whether a failure is formatting, Terraform state, OIDC trust, IAM authorization, or the application itself.

Keep the role reusable, but not universal

A deployment role can support more than one stack without becoming an account-wide administrator. Prefer predictable resource-name prefixes and explicit service permissions. If a second application needs a new AWS service, add that permission deliberately rather than starting with *.

State is infrastructure too

Remote state is not optional once a pipeline is applying Terraform. Version the state bucket, encrypt it, block public access, require TLS, and use Terraform's supported locking mechanism. The bootstrap layer that creates that backend also needs a recovery story—local-only bootstrap state is still a single point of operational pain.

The short version

Use OIDC for identity, STS for temporary credentials, Terraform remote state for continuity, and a repo-scoped IAM role for deployment. When it fails, check formatting and backend initialization before assuming the cloud credentials are broken.

Editorial note: this guide is based on infrastructure patterns LionsTooth Tech has implemented directly, not on a simulated benchmark.