REST API and OAuth
Can has a public REST API at https://api.can.randomfact.com. Everything the app can do to boards, tickets, tags, and comments, a script or integration can do too — with the caller's own identity and permissions.
Explore the API
- Interactive docs (Swagger UI): api.can.randomfact.com/docs
- OpenAPI spec: api.can.randomfact.com/v1/openapi.json
What is available
All endpoints live under /v1 and are scoped by workspace slug:
- Workspaces — list your memberships, read one workspace.
- Boards — list, read, create, rename.
- Columns — list a board's columns.
- Tickets — list, read, create, edit, bulk status change, semantic search, and slug-free resolution by key (
GET /v1/tickets/LAUN-7finds the ticket across all your workspaces). - Tags — full create / rename / recolor / delete.
- Comments — full thread access including one-level replies and soft-delete.
List endpoints paginate with pageSize (default 50, max 200) and an opaque cursor.
Ticket responses come in two shapes. Reading one ticket — GET .../tickets/{key} or the slug-free GET /v1/tickets/{key} — returns everything: description, attachments, timestamps. Everything else returns a summary: id, boardId, columnId, title, assigneeId, agentAssigneeId, tagIds, commentCount, updatedAt. Creating or editing a ticket answers with that summary rather than echoing the body back; listing and searching add a descriptionPreview of the description's first 160 characters, and take view=full when you really do want every field of every ticket.
Authentication
The API accepts two kinds of credentials for interactive callers:
- OAuth 2.0 access tokens — for integrations. Can runs a standard OAuth 2.0 / OpenID Connect server on the same hostname: authorization endpoint, token endpoint, and discovery document at
/.well-known/openid-configuration. Public clients use PKCE; no client secret is required. - Firebase ID tokens — what the Can app itself uses; useful for quick scripts if you already have one.
Two long-lived credentials serve headless callers: personal access tokens (below), and workspace integration credentials — the rfi_can_… token another app's workspace uses to act as itself, described in Integrations.
New OAuth clients can be created two ways:
- Dynamic client registration (
POST /oauth/register, RFC 7591) — programmatic, no manual approval, rate-limited per IP. - The Authorize button in the Swagger UI walks you through a browser sign-in for trying out endpoints by hand.
Personal access tokens
For your own scripts, CI jobs, and headless tools there is a third credential: a personal access token (PAT). A PAT is a long-lived opaque token, prefixed rft_can_, that authenticates as you — same identity, same workspace memberships, same permissions as signing in. It is you acting as you: don't hand a PAT to an agent, a connector, or another person; those should keep using OAuth (or a workspace integration credential), so access is delegated and individually revocable.
-
Create one in workspace settings under API tokens (the tokens are personal, not workspace-scoped — the section just lives there). Give it a name and, optionally, an expiry date. The token is displayed exactly once; Can stores only a hash, so copy it immediately.
-
Use it as a standard bearer token:
curl -H "Authorization: Bearer rft_can_..." \ https://api.can.randomfact.com/v1/workspaces/my-team/boards -
Revoke it from the same list at any time — revocation is instant, because every request looks the token up live. Expired tokens stop working the moment they expire and are eventually cleaned up automatically.
-
Auditability: changes made with a PAT are recorded in ticket activity with a
viavalue ofpat:<token name>, just as OAuth writes record the client name. The field rides along in board exports, and a ticket's History tab shows the name after the actor, as a mutedvia <token name>.
Permissions
Tokens identify a user, not a workspace. Every request is authorized against your live workspace membership at the moment of the call: if you are removed from a workspace or demoted from admin, the API reflects that on your very next request — no token revocation needed.
The API never reveals whether a workspace you cannot access exists; you get a 404 either way.
Auditability
Changes made through the API are recorded in ticket activity with a via value naming the caller (for example api:My Script for an OAuth client), so a board's export always distinguishes API writes from clicks in the app. Writes that reach the API through the hosted MCP server carry the same client name under an mcp: prefix, so you can tell an agent's edit from a script's. A ticket's History tab shows the name after the actor either way, as a muted via My Script.