You can manage service accounts and their authentication methods, including tokens and OpenID Connect (OIDC) configurations, using Configuration as Code (CasC). CasC allows you to declaratively define service accounts, authentication methods, and group memberships at root and item scope.
Define root-scoped service accounts
Define root-scoped service accounts and group memberships in the CasC bundle’s rbac.yaml file.
Service accounts are defined under a serviceAccounts section at the root.
Each service account definition includes a name and an authentication list.
Define item-scoped service accounts
Define item-scoped service accounts and group memberships in the CasC bundle’s items.yaml file.
Service accounts are defined under a serviceAccounts section under an item definition.
Each service account definition includes a name and an authentication list.
Configuration modes in CasC
As with Role-Based Access Control (RBAC) in CasC, you must select either SYNC or UPDATE mode within the rbac.yaml file and within each items.yaml file to specify how service accounts, authentication methods, and group memberships are managed when the configuration is applied.
-
SYNCmode: Ensures that any service accounts, authentication methods, and group memberships not defined in CasC are removed when the configuration is applied. -
UPDATEmode: Adds or modifies only the service accounts, authentication methods, and group memberships defined in CasC, leaving others unchanged.
Configure token authentication
Add a token to a service account to allow automated systems to authenticate using HTTP Basic authentication.
The following example items.yaml file defines an item-scoped service account with one token and adds the service account to a group.
|
| 1 | Configuration mode must be SYNC or UPDATE. Refer to Configuration modes in CasC. |
| 2 | Authentication type must be password. No other types are supported. |
| 3 | Mandatory id attribute uniquely identifies the token. |
| 4 | Optional description for the token’s purpose. |
| 5 | The password value (whether read from a file via ${readFile:…} or hardcoded) must begin with a cloudbees_ci_sa_ prefix, followed by exactly 32 hexadecimal characters (for example, cloudbees_ci_sa_abc123def456789012345678901234ef).
You can generate compliant tokens using standard tools, such as openssl rand -hex 16 on Linux/macOS. |
| 6 | Optional expiration in ISO-8601 format (must be quoted in YAML). |
| 7 | Item-scoped service accounts must be referenced by their full path. |
Manage token lifecycles in CasC
When applying a CasC bundle, the token behavior depends on whether the token already exists (as identified by id) and whether the password attribute is specified:
| Token type | password attribute specified |
password attribute omitted |
|---|---|---|
Existing token |
The |
The |
New token |
The token is created with the specified password. |
The token is not created, and a warning is issued. |
When you export a CasC bundle, all token fields are included except password.
This behavior enables token rotation in CasC while allowing the old token to be used temporarily.
Example: Rotate a token with temporary overlap
The following procedure shows how to rotate a token, allowing the old token to work until 2026-06-08.
-
Start with your initial service account definition:
-
Edit the bundle on
2026-06-01, to add the new token and set an expiration on the old token: -
Change the backing
Secretto a new value and apply the bundle so that both tokens work for one week. -
Update any scripts or tools to use the new token before
2026-06-08. -
After
2026-06-08, edit the bundle again to remove the old token:
Configure OIDC authentication
OIDC authentication uses a temporary JSON Web Token (JWT) from an OIDC identity provider (IdP) to authenticate a service account without requiring a long-lived token.
| A service account supports multiple OIDC configurations, but CloudBees recommends defining a separate service account for each IdP or system if you want to manage permissions for each independently. |
Prerequisites for OIDC authentication
OIDC authentication eliminates the need to manage long-lived tokens and the associated risks. It requires the following:
-
The system or script using the service account must be able to receive a temporary JWT identity token from an OIDC identity provider (IdP).
-
The service account must be configured to expect JWTs from the OIDC IdP, including specific claim values such as issuer, subject, and audience.
-
The IdP must:
-
Be accessible from the CloudBees CI network, so the operations center or controller receiving the authenticated request can contact the IdP to verify the JWT.
-
Support OpenID Connect Discovery. For a JWT with
"iss":"https://idp.example.com", the IdP must serve a JSON document athttps://idp.example.com/.well-known/openid-configurationcontaining ajwks_urifield pointing to the public key used to verify the JWT’s signature.
-
If these conditions are met, OIDC authentication is simpler to manage than tokens, because there are no secrets to store or rotate, and no special lifecycle considerations when applying bundle updates.
Supported systems for OIDC authentication
CloudBees CI supports OIDC authentication from any IdP that meets the prerequisites. The following systems are common, tested examples:
-
One or more controllers with the OpenID Connect Provider plugin installed. These can be CloudBees CI or Jenkins controllers in an unrelated CloudBees CI installation. For usage details, refer to the Jenkins OpenID Connect Provider plugin documentation.
A controller can also authenticate to itself using OIDC, for example, to modify its own CasC configuration through the REST API from a Pipeline build. -
GitHub Actions workflows.
-
A Kubernetes
Podusing service account token projection.
| OIDC authentication for service accounts is machine-to-machine authentication and is distinct from interactive user authentication through a web browser, which is the original use case for OIDC. |
Configure the CasC bundle
To configure OIDC authentication for a service account in CasC:
-
In the operations center
rbac.yamlfile, configure the list of allowed OIDC issuer domains using theserviceAccountOidcIssuerDomainsfield:1 Configuration mode must be SYNCorUPDATE. Refer to Configuration modes in CasC.2 Allows JWTs from idp.example.comand any of its subdomains. Replace with your IdP’s domain. You can list multiple domains to allow JWTs from different issuers.3 Allows JWTs from ci.example.comand any of its subdomains. An empty list (or the absence of the field) blocks all OIDC authentication. -
In the
rbac.yamloritems.yamlfile, add atype: oidcentry to the service account’sauthenticationlist:1 Configuration mode must be SYNCorUPDATE. Refer to Configuration modes in CasC.2 Identifies OIDC authentication type. 3 Uniquely identifies the OIDC configuration among authentications for this service account. 4 The issclaim value expected in the JWT, which must match the IdP’s issuer URL. The issuer URL must use thehttpsscheme.5 The subclaim value expected in the JWT, as defined by the IdP.6 Optional. The audclaim value expected in the JWT. Specify a different value only if your IdP does not allow you to control theaudclaim. Defaults to the service account URL if not specified (for example,https://cloudbees-ci.example.com/cjoc/serviceAccounts/bot/).If you are unsure what claims your IdP includes in the JWTs it issues, you can run the following command to print the claims without leaking the JWT itself or its signature:
set +x # make sure the JWT value is not printed in the logs echo $JWT | cut -d. -f2 | base64 -d 2>/dev/null | jq
Once you apply the OIDC configuration, the service account can be authenticated by any system that can obtain a JWT from the IdP with the expected claims and present it to the operations center or controller.
The operations center or controller verify the JWT’s signature using the public key obtained from the IdP’s jwks_uri and then verify that the claims match the expected values defined in CasC.
OIDC usage examples
The following examples show how to authenticate to a CloudBees CI service account using OIDC from various systems. Refer to your IdP documentation to determine exactly how to obtain a JWT with the expected claims.
|
Only |
Jenkins upstream example
To authenticate from a Jenkins controller to a CloudBees CI service account using OIDC, install and use the OpenID Connect Provider plugin on the Jenkins controller to obtain a JWT and present it to the CloudBees CI REST API or CLI.
The issuer is derived from the Jenkins controller URL, which is shown when you create the ID_TOKEN credentials, and the subject is the job URL.
CloudBees recommends setting the audience to the service account URL when configuring the ID_TOKEN credentials, in which case the audience setting may be omitted from CasC.
|
The following example shows Scripted Pipeline usage:
|
In a Declarative Pipeline, bind the credentials in an |
GitHub Actions example
The following example configures the operations center rbac.yaml to allow the GitHub Actions issuer domain and defines the service account:
You can then use it from a GitHub Actions workflow:
Kubernetes example
The following example creates a Kubernetes ServiceAccount used by a Pod that mounts its token:
The following example configures the operations center rbac.yaml and defines the service account for a Google Kubernetes Engine (GKE) cluster:
|
For an Amazon Elastic Kubernetes Service (Amazon EKS) cluster, the For example: The corresponding entry in |