Register the workload identity of the app once, as an admin, and remove the stored API key. The SDK gets an identity token from the cloud or the CI system and exchanges it for a short-lived Provely token.
The API key keeps working. A workload identity is a second way to authenticate, not a replacement that you must use.
Which identities can a workload prove?
| Provider | The proof | The subject that you register |
|---|---|---|
| GitHub Actions | The OIDC token of the workflow run | repo:acme/payments:ref:refs/heads/main |
| AWS | A signed sts:GetCallerIdentity request | arn:aws:iam::123456789012:role/payments-prod |
| GCP | The identity token of the attached service account | payments@acme-prod.iam.gserviceaccount.com |
| Kubernetes | A projected service account token | system:serviceaccount:payments:api |
| Another OIDC issuer | An identity token in a file | The sub claim of the token |
In a subject, a star matches a run of characters that holds no colon. A GitHub subject must name one literal owner and repository, so a subject for every repository is refused. A GCP subject is one exact service account email.
How do I register an identity?
Register a workload identity
- Open the pageSign in to the console as an owner or an admin. Open Account settings, then Workload identities.
- Choose the providerChoose the provider. AWS, GCP, and GitHub Actions fix the issuer. For Kubernetes and another OIDC issuer, give the https issuer URL.
- State the subjectState the subject, and any extra claims that the token must carry with an exact value.
- Copy the audienceCopy the audience that the page shows, for example
https://api.provely.sh/o/org_01EXAMPLE. SetPROVELY_WORKLOAD_AUDIENCEto it in the app.
Only a signed-in person with the admin permission registers, changes, or revokes an identity. An API key gets 403. The agent holds the API key and is untrusted, so its credential never decides who else may act for the organization.
Why does the server issue the audience?
The audience names your organization, so a token for your audience never matches the registration of another organization. A registration cannot choose another audience.
With a shared audience, another organization could register your subject and make your exchange ambiguous. The exchange then refuses, and your app stops. The audience of each organization makes this impossible.
An app that sends another audience gets audience_not_registered. The message names PROVELY_WORKLOAD_AUDIENCE and the Workload identities page.
How do I set up each provider?
GitHub Actions
Give the job the permission to request an OIDC token. The SDK reads ACTIONS_ID_TOKEN_REQUEST_URL and ACTIONS_ID_TOKEN_REQUEST_TOKEN, which GitHub sets when the permission is present.
permissions:
id-token: write
contents: read
env:
PROVELY_WORKLOAD_AUDIENCE: https://api.provely.sh/o/org_01EXAMPLE
AWS
Run the app with role credentials: Lambda, ECS, or any compute that sets AWS_ACCESS_KEY_ID, AWS_SECRET_ACCESS_KEY, and AWS_SESSION_TOKEN. The SDK signs one sts:GetCallerIdentity request with those credentials and sends the signed request. Provely sends it to AWS STS, and AWS states the role. No AWS credential leaves the app. Register the role ARN, not the assumed-role ARN.
PROVELY_WORKLOAD_AUDIENCE=https://api.provely.sh/o/org_01EXAMPLE
GCP
Attach a service account to the Cloud Run service, the Cloud Function, the GKE workload, or the Compute Engine instance. The SDK asks the metadata server for an identity token for the audience in PROVELY_WORKLOAD_AUDIENCE. Register the email of the service account.
Kubernetes
Mount a projected service account token with the audience of the organization at /var/run/secrets/provely/token, or set PROVELY_KUBERNETES_TOKEN_FILE to its path. The issuer of the cluster must publish its discovery document and its key set on a public https URL. EKS, GKE, and AKS do this.
volumes:
- name: provely-token
projected:
sources:
- serviceAccountToken:
path: token
audience: https://api.provely.sh/o/org_01EXAMPLE
expirationSeconds: 3600
# mount provely-token at /var/run/secrets/provely
Another OIDC issuer
Write the identity token to a file, and set PROVELY_IDENTITY_TOKEN_FILE to its path. The SDK reads the file again at each refresh, so a rotated token is used.
Which credential does the SDK use?
- The API key, when
PROVELY_API_KEYis set. - A workload identity, when the SDK detects one.
- The CLI login file that
provely loginwrites.
Get your API key: sign in at app.provely.sh/account/api-keys, open API keys, and create a key. The dashboard shows the key once. Keep it in an environment variable, never in code. Or run provely login once on your machine: the SDKs then read the key that it stores.
| Variable | What it does |
|---|---|
PROVELY_WORKLOAD_IDENTITY | auto (the default) detects the environment. off disables workload identity. github_actions, aws, gcp, kubernetes, or file selects one provider. |
PROVELY_WORKLOAD_AUDIENCE | The audience that the Workload identities page shows. Set it in production. The default, the API origin, matches no registration. |
PROVELY_IDENTITY_TOKEN_FILE | The file that holds the token of another OIDC issuer. |
PROVELY_KUBERNETES_TOKEN_FILE | The projected token file. The default is /var/run/secrets/provely/token. |
The SDK refreshes the token before it expires. It never writes the identity token or the Provely token to a log or an error.
What does the token permit?
The exchange answers the same short-lived token that POST /v1/tokens answers for an API key. The token belongs to the organization of the registration. It carries the agent scopes of a normal SDK key and no admin scope. It cannot mint another token. Runs are metered for the organization, whatever the credential.
A revoked identity stops the next exchange at once. A token that it already bought expires at its own expiry, within 15 minutes.
What does this not cover?
- The SDK does not read EC2 instance metadata credentials today. On EC2, set the role credentials in the environment, or run on ECS or Lambda.
- A stolen identity token acts as the workload until it expires. Keep the token life short at the issuer.
- GitHub and Google sign tokens for every customer. The subject is the security boundary, so register an exact subject.