API keys
Create an API key, set an expiry, and use a CI key with least privilege for pipelines.
An API key lets a script, an MCP client or a pipeline call webagent as your project. The key decides the organization, the project and the role of every call. Keys look like wa_us_xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx.
Create a key in the dashboard: API keys in the sidebar, then Create key. The full key is shown once, so save it at once (a CI secret, a password manager). The list afterwards shows only the start of the key. An admin can also create keys with POST /v1/keys and revoke one with DELETE /v1/keys/:keyId.
| Option | Values | Default |
|---|---|---|
name | A label, so you can tell keys apart | Required |
role | member or admin | member |
expiresAt | An ISO date and time in the future | Never |
scope | full or ci | full |
Make one key per job or machine, so you can revoke it alone.
Expiry
Give a key an expiry (expiresAt) when it is for a short job or a contractor. The dashboard form offers Never, 30 days, 90 days or a date you pick. It sends one expiresAt. The API refuses a time in the past, or one too far ahead, and the error message says the limit.
After that time the key stops working. A call with it fails with 401 and code unauthorized:
{ "error": { "code": "unauthorized", "message": "API key expired on 2026-11-13T00:00:00.000Z; create a new key" } }Create a new key and replace the secret in your CI. The keys list shows Expires with the date, Expired, or Never. A key made before expiry existed never expires, and keeps its full scope.
Scope: full or CI
A full key can do whatever its role allows. A ci key is for pipelines. It can run tests and read results, and nothing else. If a pipeline key leaks, it cannot change your team, billing or settings. In the list, a ci key has a CI badge.
Choose CI in the create form, or send "scope": "ci":
curl -s -X POST $API_URL/v1/keys \
-H "Authorization: Bearer $WEBAGENT_API_KEY" \
-H "Content-Type: application/json" \
-d '{"name":"github-actions","scope":"ci","expiresAt":"2027-01-31T00:00:00Z"}'(Use an admin key for this call. Set API_URL as in the Quickstart.)
What a CI key can do
| Area | Allowed |
|---|---|
| Sessions | Create, list, read, update and stop sessions. Get a session token. Read the recording and the logs. Create and remove a share link |
| Tasks | List tasks, and read a task report (GET /v1/tasks, GET /v1/sessions/:id/tasks, GET /v1/tasks/:id/report.json) |
| Skills | List and read skills, run a skill, list skill runs and read their reports |
| Workflows | List and read workflows. Save a workflow by key (PUT /v1/workflows/by-key/:key, what webagent test --sync does). Start a run (POST /v1/workflow-runs, POST /v1/workflows/:id/runs), list and read runs, read report.md, cancel a run |
| MCP | The hosted MCP endpoint, POST /mcp |
Everything else is refused, including API keys, team and organization, billing, settings, credentials, the audit log, projects, and creating, editing or deleting a workflow in the dashboard. A new route stays closed to CI keys until it is opened on purpose.
A refused call fails with 403 and code forbidden: "This is a CI key; use a full key or the dashboard for this". error.details.reason is ci_scope. A run that a CI key started before its expiry finishes normally.
Use a CI key with the GitHub Action or the Smoke tests in CI script.