The sub claim is the subject line of a GitHub Actions OIDC token. It names the repository and the trigger, such as a branch, an environment or a pull request. Your cloud role trust policy compares it to a pattern you wrote, so the exact format decides who can assume the role.
What is the sub claim?
When a workflow job asks GitHub for an OIDC token, GitHub signs a short JWT that carries several claims. Two matter most for access: aud, which says who the token is for, and sub, which says who is asking. GitHub's documentation describes sub as the subject the cloud provider checks against the conditions on the cloud role.
Think of it as a label your cloud account reads before it hands out temporary credentials. If the label is loose, many jobs can match. If it is exact, only one kind of job can.
The formats, side by side
GitHub documents three default shapes. Which one you get depends on how the job was triggered and whether it references an environment.
| Trigger | sub format |
|---|---|
| Job references an environment | repo:ORG/REPO:environment:NAME |
| Pull request event (no environment) | repo:ORG/REPO:pull_request |
| Branch push (no environment) | repo:ORG/REPO:ref:refs/heads/BRANCH |
Note the precedence. When a job references an environment, the environment name appears in the claim. The branch name appears only if the job does not reference an environment. A deploy job that targets a protected environment therefore presents a different subject than the same repository's test job on the same branch.
Newer repositories use an immutable format
GitHub's docs state that repositories created after 15 July 2026 use an immutable default subject that includes the owner and repository IDs, for example repo:OWNER@OWNER-ID/REPO@REPO-ID:ref:refs/heads/BRANCH. Repositories created before that date keep the earlier format unless you opt in. Renames and transfers after that date also move to the immutable format. GitHub Enterprise Server is not part of that rollout.
The practical point: copy the trust condition from a real token or from the current docs, not from an old blog post or a template written for the older format.
How to pin a role to the right subject
- Decide what should be allowed to deploy: one branch, one environment, or release tags.
- Prefer an environment for deploy jobs, because environments can carry protection rules. GitHub recommends adding protection rules that restrict which branches and tags can deploy when you use environments in OIDC policies.
- Write the trust condition as an exact match on
sub, not a wildcard. - Keep the audience condition too. For AWS with the official action, the audience is
sts.amazonaws.com. - Test with a throwaway workflow and read the assume role result before you rely on it.
For AWS, a condition limiting access to one branch looks like this:
"Condition": {
"StringEquals": {
"token.actions.githubusercontent.com:aud": "sts.amazonaws.com",
"token.actions.githubusercontent.com:sub": "repo:octo-org/octo-repo:ref:refs/heads/main"
}
}
Why wildcards deserve a second look
GitHub's AWS guide shows a StringLike example with repo:octo-org/octo-repo:*. It notes that this allows any branch, pull request merge branch or environment in that repository to assume the role. That may be what you want for a read only role. It is rarely what you want for a role that can write to production. The same guide says you must define at least one condition so untrusted repositories cannot request access tokens.
Quick check
Does the sub claim include the branch when I use an environment?
No. Per GitHub's documentation, the branch name appears only if the job does not reference an environment. With an environment, the claim carries the environment name.
Is a wildcard in the sub condition ever fine?
Sometimes, for roles with narrow read access. Treat it as a deliberate choice, since it lets every branch, pull request and environment in the repository match.
Safeguard does not manage your cloud accounts. It scans your code and dependencies, applies policies and gates on pull requests, and automates compliance evidence. You can try a free scan at gold.safeguard.sh/scan.
Sources
- GitHub Docs: OpenID Connect concepts
- GitHub Docs: OpenID Connect reference
- GitHub Docs: OIDC in Amazon Web Services
Last reviewed: 19 October 2026.