Skip to main content

Overview

Rhombus supports OAuth 2.0 with PKCE so you can build applications that sign users in with their existing Rhombus credentials. When a user clicks Sign in with Rhombus in your app, they’re redirected to the Rhombus Console to authenticate, then bounced back to your redirect URI with a short-lived authorization code. You exchange that code for an access token and call the Rhombus API on the user’s behalf. This is the same flow used by the official Rhombus CLIrhombus login is a working reference implementation in Go that you can read end to end. Use this guide to build:
  • CLI tools that authenticate via browser login (like the Rhombus CLI itself)
  • Web applications that let Rhombus users sign in to your service
  • Admin dashboards and internal integrations for customers that manage many Rhombus orgs
  • Desktop applications using a local-loopback redirect
What this guide isn’t. This is for third-party developers building apps that sign in Rhombus users. If you’re a Rhombus customer trying to configure SAML SSO for your employees (Okta, Azure AD, Google Workspace) or SCIM for user provisioning, see SAML SSO & SCIM Provisioning instead — that’s a separate surface from the OAuth flow described here.

How the flow works

The Rhombus OAuth surface spans three hosts. This is a common source of confusion — your app talks to all three at different stages of the flow.
HostRole
console.rhombussystems.comWhere the user signs in and approves your app
auth-web.rhombussystems.comToken exchange endpoint
api2.rhombussystems.comAPI calls made with the resulting access token

Before you begin

Before you start, make sure you have:
  • A Rhombus account with an API key (generated in the Rhombus Console under Settings → API Management)
  • A redirect URI your app controls — a public HTTPS URL in production, or http://localhost:<port>/callback for CLI and desktop apps
  • Basic familiarity with OAuth 2.0 Authorization Code flow and PKCE (RFC 7636)

Step 1: Register your application

Before you can start an OAuth flow, Rhombus needs to know about your application. Registration gives you a clientId and clientSecret pair. There are two paths to a clientId, depending on where you are in your build:

Prototyping & development

Call the submitApplication API directly with your existing API key. Fastest path to a working flow on localhost. Self-serve, immediate.

Production & distribution

Apps that will be shipped to customers or accept logins from users outside your own organization must be reviewed by Rhombus. Contact your Rhombus representative or post in the Developer Community to start review.
Production OAuth applications require Rhombus review. You can self-register a clientId with the API call below for local development and testing, but do not distribute apps to end users with a self-registered clientId — Rhombus may rate-limit or revoke unreviewed production use. Start a review as soon as your prototype works.

Register with the API

POST /api/oauth/submitApplication returns a fresh clientId and clientSecret. Store the clientSecret securely — it is not retrievable later.
Example response:
Additional endpoints are available to manage registered applications: getAllApplicationsForOrg, getApplicationByClientId, updateApplication, and deleteApplication. See the API Reference under the OAuth tag.

Step 2: Build the authorization URL

Rhombus uses PKCE (Proof Key for Code Exchange) to protect against authorization code interception. For every login attempt, generate:
  • A code verifier — a 43–128 character URL-safe random string
  • A code challenge — the SHA-256 hash of the verifier, base64url-encoded (without padding)
  • A state parameter — an unguessable random value used to prevent CSRF
Persist the codeVerifier and state alongside the user’s session (or, for CLI tools, in process memory) until the callback lands. You’ll need both.
The authorization endpoint uses standard OAuth 2.0 parameter names — client_id, redirect_uri, response_type=code, state, code_challenge, and code_challenge_method=S256. Only S256 is supported for the challenge method. (For backward compatibility the console also accepts the short forms redirect and challenge, but prefer the standard names shown above.)
Redirect the user’s browser to the URL you built. They’ll sign in to Rhombus and approve your application.

Step 3: Handle the redirect callback

After the user authenticates, Rhombus redirects to your redirectUri with query parameters: On success, the callback carries:
ParameterDescription
codeAuthorization code to exchange for an access token. Short-lived.
stateThe state value you sent — you must verify it matches.
iss(when configured) The issuer identifier (RFC 9207). If present, validate it matches the expected authorization server.
On failure, the callback carries error (e.g., access_denied) and error_description (human-readable detail) instead of code.
Always verify the state parameter matches what you sent. A mismatch indicates a possible CSRF attack — abort the flow.

Step 4: Exchange the code for an access token

Call POST https://auth-web.rhombussystems.com/oauth/token with the authorization code and your PKCE verifier. This is a standard OAuth 2.0 token request: send the parameters form-encoded (application/x-www-form-urlencoded), not as JSON, and authenticate your client with its clientId/clientSecret — either via HTTP Basic auth (client_secret_basic) or in the request body (client_secret_post, shown below). This is a different host from the main API — the /oauth/token endpoint lives on auth-web.rhombussystems.com.
Example response:

Step 5: Call the Rhombus API

Use the access token with two headers on every Rhombus API call:
  • x-auth-scheme: api-oauth-token
  • x-auth-access-token: <accessToken>
This is different from the standard API key scheme (api-token + x-auth-apikey) — OAuth access tokens use their own scheme identifier so Rhombus can apply OAuth-specific authorization.
If this call returns a list of users, your OAuth flow is working end to end. The user has authenticated, you have an access token, and you’re calling the API on their behalf.

Access token lifetime

The expires_in field on the token response tells you how long (in seconds) the access token is valid (typically one hour). When it expires, the Rhombus API will return an authentication error. For long-lived access — background services, daemons, scheduled jobs, or any client that cannot re-prompt the user — mint a durable API key using the OAuth access token (see next section) rather than trying to maintain a refreshed OAuth session. This is the pattern the Rhombus CLI uses.
A refresh_token is returned alongside the access token. You can exchange it for a new access token by calling the same /oauth/token endpoint with grant_type=refresh_token and refresh_token=<token> (plus your client authentication). For long-lived, non-interactive access — background services, daemons, scheduled jobs — prefer minting a durable API key (see below) rather than maintaining a refreshed OAuth session. This is the pattern the Rhombus CLI uses.

Mint a long-lived API key

Once a user has signed in with OAuth, you can trade the short-lived access token for a permanent API key. This is what rhombus login does so the CLI can continue making API calls after the browser session ends. Call POST /api/integrations/org/submitApiTokenApplication with x-auth-scheme: api-oauth-token and x-auth-access-token: <accessToken>:
From that point on, use the API key with the standard x-auth-scheme: api-token + x-auth-apikey headers — no further OAuth calls required. The CLI also supports a certificate-based (mTLS) variant of this flow for higher-security deployments; see cmd/login.go for the full implementation.
Treat minted API keys like passwords. They are long-lived and confer the same permissions as the user who created them. Store them encrypted at rest, never in source control, and rotate or delete unused keys.

Working with partner accounts

“Sign in with Rhombus” issues user-scoped OAuth tokens — they act within the organization the user belongs to. The OAuth flow does not distinguish partner accounts, and the callback does not tell you whether the user is a partner. For partner/MSP scenarios — where you need to act across multiple client organizations — use the Partner API instead of OAuth. It relies on a partner-scoped API key:
  • Send x-auth-scheme: partner-api-token with your partner API key
  • Target a specific client organization by adding its UUID in the x-auth-org header on each call
See Partner API Calls for the full pattern.

Reference implementation

The Rhombus CLI is a production reference for everything in this guide. cmd/login.go walks the full flow end to end: PKCE generation, local callback server, authorization URL construction, token exchange, mTLS API-key minting, and credential persistence. If something in your implementation isn’t working, diff your behavior against the CLI — it’s the canonical example.

Troubleshooting

Your callback received a state value different from what you sent. Verify you’re persisting the state you generated in Step 2 alongside the user’s session (or in memory for CLI tools) and comparing it on the callback. A persistent mismatch can indicate a CSRF attempt — abort the flow rather than retrying silently.
Common causes:
  • redirect_uri mismatch — the redirect_uri in the token exchange body must match exactly (including scheme, host, port, and path) the redirect_uri you sent in Step 2 and the URI registered with your OAuth application.
  • Expired code — authorization codes are short-lived (seconds, not minutes). Exchange them immediately on callback.
  • code_verifier doesn’t hash to code_challenge — verify you’re using SHA-256 and base64url encoding without = padding on both the challenge generation and the verifier transmission.
  • Wrong content type or client auth — the token endpoint expects application/x-www-form-urlencoded (not JSON), and your clientId/clientSecret must be sent via HTTP Basic auth or in the form body (client_secret_post). The token request does not use an x-auth-scheme header.
Check the headers. OAuth access tokens use x-auth-scheme: api-oauth-token and x-auth-access-token: <token>. Using x-auth-apikey (the API key header) with an OAuth access token will fail — those are different schemes with different header names.
The client_id you’re sending may be unrecognized. Double-check you’re using the clientId returned from submitApplication, not the application UUID from a different response. If you rotated applications, the old clientId is no longer valid.

Next steps

Rhombus CLI

Read how the official CLI uses this flow end to end

API Reference

Browse all endpoints available once you have an access token

Rate Limits

Understand request limits before you ship

Developer Community

Request production OAuth review and ask questions
Last modified on July 8, 2026