You can manage service accounts and their tokens using Configuration as Code (CasC). CasC provides declarative configuration to define service accounts, tokens, and group memberships at root and item scope.
Define root-scoped service accounts
Define root service accounts and memberships in root-scoped groups 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 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 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, tokens, and group memberships are managed when the configuration is applied.
-
SYNCmode: Ensures that any service accounts, tokens, and group memberships not defined in CasC are removed when the configuration is applied. -
UPDATEmode: Adds or modifies only the service accounts, tokens, and group memberships defined in CasC, leaving others unchanged.
Example CasC configuration
The following example items.yaml 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:
serviceAccounts: - name: bot authentication: - type: password id: bot-token password: ${readFile:/run/secrets/bot-token} -
Edit the bundle on
2026-06-01, to add the new token and set an expiration on the old token:serviceAccounts: - name: bot authentication: - type: password id: bot-token description: deprecated, please switch to new token expiration: '2026-06-08T00:00:00Z' - type: password id: new-bot-token password: ${readFile:/run/secrets/bot-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:serviceAccounts: - name: bot authentication: - type: password id: new-bot-token password: ${readFile:/run/secrets/bot-token}