Authenticated Hodoflow APIs use an OAuth2-style service-account
client_credentials exchange. There is no user-password API login, no
long-lived bearer API key, and no refresh token.
An owner or admin creates the service account in the intended workspace,
selects an active run-as member, and grants the smallest applicable scopes.
The client ID and secret are then exchanged for a short-lived bearer token at
POST /api/v1/oauth/token.
For the complete reproducible path, begin with Make your first API request.
Lifecycle at a glance
- Select the target workspace in the Hodoflow application.
- Create a specifically named service account.
- Choose an active run-as member whose access should bound the integration.
- Grant
api_read,api_write, orwebhooksonly as required. - Capture the client secret once into your normal secret manager.
- Exchange credentials and cache the token for slightly less than
expires_in. - Send
Authorization: Bearer $TOKENon protected requests. - Rotate with an overlap window, then promote the staged pair.
- Revoke or deactivate immediately when access is no longer needed.
Token exchange
The canonical endpoint accepts JSON credentials or HTTP Basic authentication
and requires grant_type: client_credentials. A successful response contains:
{
"access_token": "<redacted JWT>",
"token_type": "bearer",
"expires_in": 900
}
The lifetime is configurable; 900 seconds is the default. Trust the returned
value instead of hard-coding it. Cache one token per service account, refresh
slightly early, and coordinate concurrent refreshes so a fleet does not stampede
the exchange endpoint. See Exchange credentials.
Runtime authorization
The bearer token identifies a service account, but it does not freeze mutable authorization until expiration. On every request Hodoflow reloads and validates:
- the active service account and its current scopes;
- the stored organization and workspace;
- the selected run-as membership and its active state; and
- the requested object's own authorization policies.
This makes deactivation, revocation, scope removal, workspace changes, and
membership changes effective for already minted tokens. A 404 can mean an
object is not visible to the run-as member; the API does not reveal filtered
object existence.
Least-privilege scopes
| Scope | Purpose |
|---|---|
api_read |
Safe JSON:API methods and GraphQL factQuery |
api_write |
Unsafe JSON:API create/update operations |
webhooks |
Webhook ingestion for triggers selecting this exact service account |
Scopes do not replace the run-as member's authorization. The service account must pass both checks. Read Scopes and run-as permissions before granting write or webhook access.
Secret handling
Never put a client secret or bearer token in a URL, source file, committed
.env, shell history, browser storage, analytics event, screenshot, generated
share link, or support message. Use environment variables only as a handoff from
your normal process secret store. Redact credentials and request bodies before
logging; keep the non-secret x-request-id for correlation.
For safe rollover and emergency shutdown, continue with Rotate and revoke credentials.