Clients, Projects & Tokens

These endpoints let a client app manage the account-side resources: clients (organizations), projects that belong to a client, and the API tokens used to authenticate. All endpoints accept either a session cookie (__Host-aius_session) or a bearer aius_… token, unless noted. Your identity is derived from the credential — you cannot act on another user’s resources.

Clients (organizations)

A client is an organization that owns projects, billing, and tokens. A default client is created automatically when you register.

List clients

GET /v1/clients
curl https://aius.co/api/v1/clients \
  -H "Authorization: Bearer aius_xxxxxxxx..."
Response 200:
{
  "data": [
    {
      "id": "client_xyz789",
      "name": "Acme Corp",
      "role": "owner",
      "created_at": 1717123456
    }
  ]
}

Create a client

POST /v1/clients
curl -X POST https://aius.co/api/v1/clients \
  -H "Authorization: Bearer aius_xxxxxxxx..." \
  -H "Content-Type: application/json" \
  -d '{"name": "Acme Corp"}'
Response 200:
{
  "id": "client_xyz789",
  "name": "Acme Corp",
  "owner_id": "usr_abc123",
  "created_at": 1717123456
}
The owner is set from your authenticated identity (a user id); you do not send owner_id.

Projects

A project belongs to a client. List/create operations are scoped by the client id.

List projects

GET /v1/projects?org_id=<client_id>
The org_id query parameter (the client id) is required.
curl "https://aius.co/api/v1/projects?org_id=client_xyz789" \
  -H "Authorization: Bearer aius_xxxxxxxx..."
Response 200:
{
  "data": [
    {
      "id": "proj_123",
      "org_id": "client_xyz789",
      "name": "Churn analysis",
      "description": "Q3 churn model",
      "created_at": 1717123456,
      "updated_at": 1717123456
    }
  ]
}

Create a project

POST /v1/projects
curl -X POST https://aius.co/api/v1/projects \
  -H "Authorization: Bearer aius_xxxxxxxx..." \
  -H "Content-Type: application/json" \
  -d '{
    "org_id": "client_xyz789",
    "name": "Churn analysis",
    "description": "Q3 churn model"
  }'
FieldTypeRequired
org_idstringYes — the owning client id
namestringYes
descriptionstringNo
Response 200: the created project (same shape as the list item above).

Get a project

GET /v1/projects/{project_id}
curl https://aius.co/api/v1/projects/proj_123 \
  -H "Authorization: Bearer aius_xxxxxxxx..."

Delete a project

DELETE /v1/projects/{project_id}
curl -X DELETE https://aius.co/api/v1/projects/proj_123 \
  -H "Authorization: Bearer aius_xxxxxxxx..."
Response 200: { "deleted": true } Accessing a project in a client you don’t belong to returns 403 NO_ACCESS; an unknown id returns 404 NOT_FOUND.

Fork a project

Create a point-in-time copy of a project as a brand-new project. The fork duplicates the brief, artifacts, and reports, records its lineage (forked_from_id), and gets an auto-uniqued name — <name> (fork), then <name> (fork 2), <name> (fork 3), … <name> (fork N) if that name is already taken. The original project is untouched.
POST /v1/projects/{project_id}/fork
curl -X POST https://aius.co/api/v1/projects/proj_123/fork \
  -H "Authorization: Bearer aius_xxxxxxxx..."
You may optionally send { "name": "...", "target_org_id": "client_abc" } to override the fork’s name or land it in another of your clients (ADR-0059) — omit the body for the classic same-client fork. Response 200: the new project, e.g. { "id": "proj_456", "name": "Churn analysis (fork)", "forked_from_id": "proj_123", ... }

Transfer a project

Move a project from one of your clients to another you also own (ADR-0059) — the destructive counterpart to fork (re-points the project’s org_id instead of copying). Both clients must be yours; billing follows the destination client.
POST /v1/projects/{project_id}/transfer
curl -X POST https://aius.co/api/v1/projects/proj_123/transfer \
  -H "Authorization: Bearer aius_xxxxxxxx..." \
  -H "Content-Type: application/json" \
  -d '{"target_org_id": "client_abc"}'
Response 200: the moved project (now with the destination org_id).

Tokens

API tokens are the aius_… credentials you use as bearer tokens. Minting requires a session (cookie), not a bearer token. Listing and revoking also require a session.

Mint a token

POST /v1/tokens
See Authentication › Mint an API token for the full flow. Briefly:
curl -X POST https://aius.co/api/v1/tokens \
  -H "Content-Type: application/json" \
  --cookie "__Host-aius_session=eyJ..." \
  -d '{"token_name": "my-cli"}'
Response 200:
{
  "id": 42,
  "client_id": "org_a1b2c3d4e5f6",
  "token_name": "my-cli",
  "token": "aius_xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx",
  "created_at": 1717123999
}
A token’s client_id is the organization id (an org_… value) it bills against — never an email. If you pass client_id when minting, send an org id you own; omit it to default to your account’s org.

List tokens

GET /v1/tokens
curl https://aius.co/api/v1/tokens \
  --cookie "__Host-aius_session=eyJ..."
Response 200: { "data": [ ... ] }. The secret token value is never returned again after minting — only metadata is listed.

Revoke a token

POST /v1/tokens/revoke
curl -X POST https://aius.co/api/v1/tokens/revoke \
  -H "Content-Type: application/json" \
  --cookie "__Host-aius_session=eyJ..." \
  -d '{"id": 42}'
Response 200: { "id": 42, "revoked_at": 1717124500 }. A revoked token is rejected on all subsequent requests with 401 invalid token. Missing id400; unknown id → 404.

Billing (overview)

Billing is in AIUS tokens. The token balance is held at the account-owner level and allocated across the owner’s clients (ADR-0060): read it with GET /v1/owner/balance and move tokens to a client with PUT /v1/owner/orgs/{org_id}/allocation. Each client also exposes Stripe-backed endpoints (subscription checkout, token top-ups and balance, invoices, payment methods, and a billing portal) under /v1/clients/{client_id}/…, typically driven from the web dashboard. See Billing for details.