Skip to content
Select theme
  • Auto
  • Dark
  • Light

Single sign-on

Telesphorepo can sign admins in through any OpenID Connect provider, such as Keycloak, Entra ID or Google.

SSO is for admins. Every SSO user is an admin. Publishers use local accounts, devices and trust policies.

  • The server creates an oidc account at the first SSO sign-in. It identifies the account by the pair issuer and subject.
  • An SSO account has no usable password. It cannot create read tokens, cannot use Basic auth, and cannot change a password.
  • An SSO account has no second factor in Telesphorepo. Your identity provider handles it.
  • The session lasts oidc.session_ttl. The default is 12 hours.
  • The username comes from the preferred_username claim. The server lower-cases it and replaces every character outside [a-z0-9._-] with -. If a different account already owns that name, the login fails with username_conflict. The server never merges accounts by name.

The server checks on every sign-in that the user is an admin. A user passes if either rule matches:

  1. Claim rule. The claim named by oidc.admin_claim (default groups) contains one of the values in oidc.admin_values. The claim can be a string or a list. A dotted path such as realm_access.roles is allowed. The server reads the ID token first, then UserInfo.
  2. Email rule. The email is verified and is in oidc.admin_emails.

You must set at least one of oidc.admin_values or oidc.admin_emails.

If a user fails the check, the server creates no account. If the account exists, the server deletes its sessions. When you remove a user from the admin group, access ends at the next sign-in attempt.

  1. In Keycloak, create a client in your realm.

    • Client type: OpenID Connect
    • Client authentication: on (a confidential client)
    • Standard flow: on
    • Valid redirect URI: https://repo.acme.com/api/auth/oidc/callback
  2. Copy the client secret from the Credentials tab.

  3. Create a group, for example telesphorepo-admins, and add your admins.

  4. Add a group membership mapper to the client scope, so that the ID token carries a groups claim. Turn off Full group path, so the value is telesphorepo-admins and not /telesphorepo-admins.

  5. In Telesphorepo, open Settings, group sso, and enter the values below. You can also use environment variables.

  6. Test the settings, then save.

Setting Value
OIDC issuer URL https://keycloak.acme.com/realms/acme
Client ID telesphorepo
Client secret the secret from step 2
Admin claim groups
Admin claim values telesphorepo-admins

SSO turns on when oidc.issuer is set.

Setting Default Notes
oidc.issuer none Setting it turns SSO on. Trailing slashes must match the provider exactly
oidc.client_id none Required
oidc.client_secret none Required. Stored encrypted. The API never returns it
oidc.redirect_url base_url + /api/auth/oidc/callback Register this URL at the provider. Either this or base_url must be set
oidc.scopes openid profile email
oidc.admin_claim groups Dotted paths allowed
oidc.admin_values none Values of the claim that make a user an admin
oidc.admin_emails none Verified emails that are admins
oidc.session_ttl 12h
admin_password_login true See below

When you save a change to the issuer, client, redirect URL or scopes, the server fetches the discovery document first. If that fails, nothing is saved and the error appears under the issuer field. The POST /api/settings/oidc/test route runs the same check without saving.

When SSO works, you can set admin_password_login to false. Local admins can then no longer sign in to the UI with a password. Publishers with local accounts still can.

The server accepts this only while an issuer is set.

A failed SSO sign-in sends the browser to /#/login?error=<code>.

Code Cause
not_authorized The user matches neither the claim rule nor the email rule
username_conflict Another account already has this username
invalid_username The server cannot build a valid username from the token
account_disabled An admin disabled the account
sso_failed Any other failure, such as a bad ID token

The login route answers 404 when SSO is off, and 503 when the server cannot reach the provider.

  • The state of a sign-in lasts 10 minutes and works once. A reload of the callback page fails with 400. Start again from the sign-in page.
  • The server refuses state from before a change of issuer or client.
  • If the stored client secret cannot be decrypted (for example, after a lost master key), the server logs an error and turns SSO off at startup. Enter the secret again. Invalid TR_OIDC_* values stop the server from starting.
  • The identity provider for admin sign-in is separate from the one a CI system uses for publishing. A trust policy has its own issuer. See Trust policies.