Skip to content

IAM / Task

Use service accounts

Updated · 4 min read

Create a service account for CI and scripts, exchange its client ID and secret for an access token, grant it roles, and revoke it.

On this page7 sections

A service account is a non-interactive credential for automation such as CI pipelines, scripts and infrastructure-as-code tools. It belongs to one organization and acts as its own principal, service_account:<service-account-id>. Its access is checked exactly like a user’s: it can do what its role assignments allow, and nothing else.

A service account authenticates with an OAuth 2.0 client ID and client secret, using the client credentials grant against the platform’s identity provider. The resulting access token is sent to the API like a user’s.

Before you begin

Create a service account

  1. Create the service account with a name that tells you what uses it.

    terminal
    origin iam create-service-account --org-id <org-id> --name ci-deploy

    The output contains the service account’s id, its principal, and the credential: clientId and clientSecret.

  2. Grant the service account the roles it needs. A new service account holds no roles and can’t do anything until you assign one. Use the principal from the previous step.

    terminal
    origin iam assign-role --org-id <org-id> \
      --project-id <project-id> \
      --principal service_account:<service-account-id> \
      --role-urn urn:origin:cloud:iam::::tc/role/roles/viewer

    Grant the smallest role and scope that does the job. See Assign and revoke roles.

  3. Verify that the service account is listed as active. An active service account has no revokedAt value.

    terminal
    origin iam list-service-accounts --org-id <org-id>

Get an access token

The origin CLI logs in people only. Automation that runs as a service account calls the GraphQL API directly.

  1. Request an access token from the token endpoint with the client credentials grant.

    terminal
    curl -s \
      https://auth.origincloud.eu/realms/origincloud/protocol/openid-connect/token \
      -d grant_type=client_credentials \
      -d client_id=<client-id> \
      -d client_secret=<client-secret>

    The response is JSON with an access_token and its lifetime in seconds, expires_in. Request a new token when it expires.

  2. Send the token as a bearer token with each API request.

    terminal
    curl -s https://api.origincloud.eu/graphql \
      -H "Authorization: Bearer <access-token>" \
      -H "Content-Type: application/json" \
      -d '{"query":"{ iam { permissions { key } } }"}'
  3. Verify that the token is accepted: the response contains a data object rather than an authentication error.

Revoke a service account

Revoking a service account disables its credential. From that moment, every request for a new access token is refused. An access token issued before the revocation stays valid until it expires.

  1. Find the service account’s ID with list-service-accounts.

  2. Revoke it.

    terminal
    origin iam revoke-service-account --org-id <org-id> \
      --service-account-id <service-account-id>
  3. Revoke its role assignments as well. Revoking the service account leaves them in place, and removing them cuts off any access token that is still valid, because roles are checked on every request.

    terminal
    origin iam remove-member --org-id <org-id> \
      --principal service_account:<service-account-id>
  4. Run list-service-accounts again and check that the service account has a revokedAt time. Revoked service accounts stay in the list. A revoked service account can’t be reactivated.

Rotate a client secret

A client secret can’t be changed or shown again. To rotate it, replace the service account with a new one:

  1. Create a new service account, as in Create a service account, and store its client secret.

  2. List the old service account’s role assignments, with their project scope:

    terminal
    origin iam principal-grants --org-id <org-id> \
      --principal service_account:<old-service-account-id>
  3. Assign the same roles, at the same scopes, to the new service account’s principal with origin iam assign-role.

  4. Switch your automation to the new client ID and secret.

  5. Revoke the old service account and remove its role assignments, as in Revoke a service account.

Using the API

The mutations are createServiceAccount and revokeServiceAccount; the query is serviceAccounts, all in the iam namespace. serviceAccounts never returns a client secret.

GraphQL
mutation {
  iam {
    createServiceAccount(input: { orgId: "<org-id>", name: "ci-deploy" }) {
      id
      principal
      clientId
      clientSecret
    }
  }
}