Instance Admin API
A grab-bag of instance-scoped REST endpoints that don't fit neatly into the other API pages: general and experimental instance settings, on-demand database backups, the LLM reflection endpoints, environments (sandbox/runtime drivers), and execution-workspace lifecycle.
These surfaces are stable enough to call from your own tooling, but they are intentionally narrow — most operators reach them through the UI, the CLI, or via the paperclipai doctor command rather than by hand.
All routes are mounted under
/api. Most require instance-admin or board authentication; per-route notes call out exceptions.
Instance settings
| Endpoint | Purpose |
|---|---|
GET /api/instance/settings |
Read the full instance-settings record (general and experimental blocks together, plus the instance default environment). Readable by any authenticated org member. |
PATCH /api/instance/settings |
Update the settings record. Body is validated against patchInstanceSettingsSchema. Setting defaultEnvironmentId picks the instance default execution environment. |
GET /api/instance/settings/general |
Read general instance settings (display name, defaults, etc.). |
PATCH /api/instance/settings/general |
Update general settings. Body is validated against patchInstanceGeneralSettingsSchema. |
GET /api/instance/settings/experimental |
Read the experimental-features block. |
PATCH /api/instance/settings/experimental |
Toggle experimental features. Body is validated against patchInstanceExperimentalSettingsSchema. |
The two GET routes only need authenticated org access; every PATCH requires instance-admin (a local_implicit board session in local trusted mode also passes). On a cloud-managed instance the platform pins executionMode in general settings, so an attempt to change it returns 403 with code execution_mode_platform_managed; settings the hosting operator has hidden are likewise floored with code settings_operator_managed, though a same-value write always passes.
General settings no longer have a keyboardShortcuts field. Keyboard shortcuts are always on for every signed-in user, so there's no instance switch and no personal preference to read or change. The general-settings patch body is strict: sending keyboardShortcuts now fails with 400. The per-user preferences endpoints that briefly held a personal shortcuts switch have been removed too.
The experimental-settings response and patch body include enableBuiltInAgents as a boolean. Set it to true before using the Built-in Agents API; while it is off, those routes return 404 Not Found.
Task drain
Task drain is an instance-wide pause on picking up new work: while it is on, agents stop being handed fresh tasks so you can wind the instance down cleanly (before a restart or maintenance window, say) without cancelling what is already running.
| Endpoint | Purpose |
|---|---|
GET /api/instance/task-drain |
Read the current drain status (whether draining, and when it started/expires). Readable by any authenticated org member. |
POST /api/instance/task-drain |
Start (or refresh) a drain. Body is validated against startTaskDrainRequestSchema; pass an optional ttlMs to have the drain expire automatically after that many milliseconds, or omit it for a drain that stays on until you stop it. Returns the resulting drain state. |
DELETE /api/instance/task-drain |
Stop draining. Returns { "wasActive": <boolean> } — whether a drain was in effect when you called. |
Reading the status needs only authenticated org access; starting and stopping a drain require instance-admin. Overlapping start/stop calls are serialised, so the audit log and the live drain state always agree.
Cloud lifecycle
These two routes exist for instances managed by Paperclip Cloud, so the Cloud control plane can keep its view of your organization's archive state in step with the instance. On a self-hosted instance both return 404 with { "error": "not_cloud_managed" }. Both require instance-admin.
| Endpoint | Purpose |
|---|---|
GET /api/instance/lifecycle |
Report the Cloud-pinned primary company's state: primaryCompanyId, primaryCompanyStatus ("missing" if that company no longer exists), and otherUnarchivedCompanyCount. |
POST /api/instance/lifecycle/unarchive-primary |
Bring an archived primary company back to active — what happens when you resume an organization from Paperclip Cloud. Returns { "status": ..., "changed": true }, or changed: false if the company wasn't archived. Returns 404 with primary_company_not_found if the company is gone. |
Database backups
POST /api/instance/database-backups
Trigger a manual database backup. Returns a structured result that includes the backup directory, retention policy, and timing. Scheduled backups follow the same code path but are not exposed as a separate route.
Instance-admin only.
Claim first instance admin
POST /api/bootstrap/claim
On a brand-new private instance that requires login, this lets the first person to sign in promote themselves to instance_admin — no manual database seeding. The first caller to claim wins; everyone after them is locked out.
Availability. This route only exists when the instance runs with deploymentMode set to authenticated and deploymentExposure set to private. On any other configuration it returns 404 with Browser first-admin claim is not available.
Cloud-managed instances. If your instance is managed by a Paperclip control plane rather than run by you, you never meet this claim screen at all — the instance comes up ready to use. The control plane owns identity there, and the users it signs in are deliberately never given the instance_admin role, so GET /api/health skips the first-admin check entirely and always reports bootstrapStatus: "ready". Self-hosted instances are unaffected: if you run the server yourself, the claim flow behaves exactly as described here.
Authentication. The caller must be a signed-in browser session (a board actor whose session source is the browser). Other callers — agents, CLI tokens, unauthenticated requests — get 401 with Sign in from a browser session before claiming first admin.
Behaviour. If no instance_admin exists yet, the signed-in user is promoted to instance_admin. The claim is atomic — the table is locked so exactly one user can win. If the instance has already been claimed, the route returns 409 with Someone else has already claimed this instance.
The request takes no body. On success the response is:
{ "claimed": true, "userId": "<the promoted user's id>" }
LLM agent-configuration reflection
These endpoints exist so agents can introspect what server-side adapters and icons are available to them.
| Endpoint | Purpose |
|---|---|
GET /api/llms/agent-configuration.txt |
Plain-text dump of available agent adapters and their declared shape. |
GET /api/llms/agent-configuration/:adapterType.txt |
Same, scoped to one adapter type. |
GET /api/llms/agent-icons.txt |
List of supported agent-icon names (AGENT_ICON_NAMES). |
Access is limited to board callers and agents whose permissions include canCreateAgents — the routes return 403 otherwise.
Environments
Environments are the plugin-managed execution backends declared by environment-driver plugins (custom sandboxes, runners, etc.).
| Endpoint | Purpose |
|---|---|
GET /api/companies/:companyId/environments |
List configured environments for the company. |
GET /api/companies/:companyId/environments/capabilities |
List the capabilities reported by available environment drivers. |
POST /api/companies/:companyId/environments |
Create an environment. Body validated against createEnvironmentSchema. |
POST /api/companies/:companyId/environments/probe-config |
Probe a candidate environment config without persisting. Body validated against probeEnvironmentConfigSchema. |
GET /api/environments/:id |
Read one environment. |
PATCH /api/environments/:id |
Update an environment. Body validated against updateEnvironmentSchema. |
DELETE /api/environments/:id |
Delete an environment. |
POST /api/environments/:id/probe |
Probe an existing environment (driver health check). |
GET /api/environments/:id/leases |
List active leases on the environment. |
GET /api/environment-leases/:leaseId |
Read a single lease. |
Execution workspaces
Execution workspaces are the materialised working directories Paperclip creates for an issue run.
| Endpoint | Purpose |
|---|---|
GET /api/companies/:companyId/execution-workspaces |
List execution workspaces for the company. |
GET /api/execution-workspaces/:id |
Read one workspace. |
GET /api/execution-workspaces/:id/close-readiness |
Whether the workspace is safe to close (no pending operations, no dirty state). |
GET /api/execution-workspaces/:id/workspace-operations |
List the operations recorded against the workspace. |
PATCH /api/execution-workspaces/:id |
Update a workspace. Body validated against updateExecutionWorkspaceSchema. |
POST /api/execution-workspaces/:id/runtime-services/:action |
Run a runtime-service control action against the workspace. |
POST /api/execution-workspaces/:id/runtime-commands/:action |
Run a runtime-command control action against the workspace. Both routes share the workspaceRuntimeControlTargetSchema body and the same handler. |
Related
- Reference → Adapters API — adapter registry endpoints.
- Reference → Plugins API — plugin install and lifecycle.
- Reference → Deployment → Environment Variables — the env-vars these admin surfaces interact with.