# Organization

> Your organization, its wake page and signed-access keys, organizations you manage for others, and deleting your own.

Every key acts as one organization. `GET /v1/org` is the probe the CLI uses to prove an endpoint and a key; it answers the key's own organization and nothing else. An organization that manages others can act inside them with the header `X-Rytiv-Org: <org id>` (see [REST API basics](https://docs.rytiv.com/reference/api-basics.md)).

## Endpoints

- [`GET /v1/org`](#get-v1org): The key's own organization, and who manages it, if anyone
- [`DELETE /v1/org`](#delete-v1org): Deletes your own organization. It must be empty
- [`GET /v1/org/wake-page`](#get-v1orgwake-page): The page shown while a sleeping app wakes
- [`PUT /v1/org/wake-page`](#put-v1orgwake-page): Sets that page (HTML)
- [`DELETE /v1/org/wake-page`](#delete-v1orgwake-page): Restores the default wake page
- [`GET /v1/org/signed-access`](#get-v1orgsigned-access): The organization's settings for signed links
- [`PUT /v1/org/signed-access`](#put-v1orgsigned-access): Changes those settings
- [`POST /v1/org/signed-access/keys`](#post-v1orgsigned-accesskeys): Adds a signing key
- [`DELETE /v1/org/signed-access/keys/:id`](#delete-v1orgsigned-accesskeysid): Removes a signing key
- [`POST /v1/orgs/managed`](#post-v1orgsmanaged): Creates an organization that yours manages
- [`GET /v1/orgs/managed`](#get-v1orgsmanaged): The organizations yours manages
- [`POST /v1/orgs/managed/:id/release`](#post-v1orgsmanagedidrelease): Hands a managed organization over to itself; your keys stop acting in it

## GET /v1/org

The key's own organization, and who manages it, if anyone.

**Auth:** Any API key, whatever its scopes. Every class of agent token may call it.

### Example request

```bash
curl -X GET "https://api.rytiv.app/v1/org" \
  -H "Authorization: Bearer $RYTIV_TOKEN"
```

### Response

`200` with the organization:

```json
{
  "id": "<id>",
  "name": "my-app",
  "createdAt": "2026-10-21T09:00:00Z"
}
```

| Field | Type | Present | Description |
| --- | --- | --- | --- |
| `id` | string | always | The organization's id. |
| `name` | string | always | Its name. |
| `createdAt` | string (ISO 8601) | always | When it was created. |
| `managedBy` | string or null | if set | The id of the organization that manages this one, or null. |
| `managedByName` | string or null | if set | That organization's name, or null. |

### Errors

| Status | Code | Meaning |
| --- | --- | --- |
| 401 | `unauthenticated` | No API key, or one that does not work. |

## DELETE /v1/org

Deletes your own organization. It must be empty.

**Auth:** API key with full access (a key with scopes cannot call this route). Refused for every agent token (`agent-token-credential`).

### Request body

JSON, the shape `OrgSelfDeleteRequest` of the contract.

| Field | Type | Required | Description |
| --- | --- | --- | --- |
| `confirmName` | string | required | 1 to 120 characters. |

### Example request

```bash
curl -X DELETE "https://api.rytiv.app/v1/org" \
  -H "Authorization: Bearer $RYTIV_TOKEN" \
  -H "Content-Type: application/json" \
  -d '{"confirmName":"<confirmName>"}'
```

### Response

`200` with a JSON object carrying `ok`, `deleted`, `removed`.

### Errors

| Status | Code | Meaning |
| --- | --- | --- |
| 400 | `bad-request` | The request is malformed or a field is out of range. `error` names every field; `issues` lists them. |
| 401 | `unauthenticated` | No API key, or one that does not work. |
| 403 | `token-scope` | The key's scopes do not cover this route. |
| 404 | `not-found` | Not found, or not yours. An object of another organization answers like one that does not exist. |

## GET /v1/org/wake-page

The page shown while a sleeping app wakes.

**Auth:** API key with full access or the scope `read`. Every class of agent token may call it.

### Example request

```bash
curl -X GET "https://api.rytiv.app/v1/org/wake-page" \
  -H "Authorization: Bearer $RYTIV_TOKEN"
```

### Response

`200` with a JSON object carrying `digest`, `bytes`, `updatedAt`, `html`.

### Errors

| Status | Code | Meaning |
| --- | --- | --- |
| 401 | `unauthenticated` | No API key, or one that does not work. |
| 403 | `token-scope` | The key's scopes do not cover this route. |

## PUT /v1/org/wake-page

Sets that page (HTML).

**Auth:** API key with full access (a key with scopes cannot call this route). An agent token of class `sandbox` or `twin` may call it; class `production` is refused (`agent-token-production-readonly`).

### Request body

JSON, the shape `SetWakePageRequest` of the contract.

| Field | Type | Required | Description |
| --- | --- | --- | --- |
| `html` | string | required | The page as HTML. |

### Example request

```bash
curl -X PUT "https://api.rytiv.app/v1/org/wake-page" \
  -H "Authorization: Bearer $RYTIV_TOKEN" \
  -H "Content-Type: application/json" \
  -d '{"html":"<html>"}'
```

### Response

`200` with a JSON object carrying `digest`, `bytes`, `updatedAt`.

### Errors

| Status | Code | Meaning |
| --- | --- | --- |
| 400 | `bad-request` | The request is malformed or a field is out of range. `error` names every field; `issues` lists them. |
| 401 | `unauthenticated` | No API key, or one that does not work. |
| 403 | `token-scope` | The key's scopes do not cover this route. |

## DELETE /v1/org/wake-page

Restores the default wake page.

**Auth:** API key with full access (a key with scopes cannot call this route). An agent token of class `sandbox` or `twin` may call it; class `production` is refused (`agent-token-production-readonly`).

### Example request

```bash
curl -X DELETE "https://api.rytiv.app/v1/org/wake-page" \
  -H "Authorization: Bearer $RYTIV_TOKEN"
```

### Response

`204` with no body.

### Errors

| Status | Code | Meaning |
| --- | --- | --- |
| 401 | `unauthenticated` | No API key, or one that does not work. |
| 403 | `token-scope` | The key's scopes do not cover this route. |

## GET /v1/org/signed-access

The organization's settings for signed links.

**Auth:** API key with full access or the scope `read`. Every class of agent token may call it.

### Example request

```bash
curl -X GET "https://api.rytiv.app/v1/org/signed-access" \
  -H "Authorization: Bearer $RYTIV_TOKEN"
```

### Response

`200` with a JSON body.

### Errors

| Status | Code | Meaning |
| --- | --- | --- |
| 401 | `unauthenticated` | No API key, or one that does not work. |
| 403 | `token-scope` | The key's scopes do not cover this route. |

## PUT /v1/org/signed-access

Changes those settings.

**Auth:** API key with full access (a key with scopes cannot call this route). Refused for every agent token (`agent-token-credential`).

### Request body

JSON, the shape `PutSignedAccessRequest` of the contract.

| Field | Type | Required | Description |
| --- | --- | --- | --- |
| `cookieTtlSeconds` | integer | optional | 60 to 86400. |
| `frameAncestors` | array of string | optional | 0 to 8 items. |

### Example request

```bash
curl -X PUT "https://api.rytiv.app/v1/org/signed-access" \
  -H "Authorization: Bearer $RYTIV_TOKEN" \
  -H "Content-Type: application/json" \
  -d '{"cookieTtlSeconds":60}'
```

### Response

`200` with a JSON body.

### Errors

| Status | Code | Meaning |
| --- | --- | --- |
| 400 | `bad-request` | The request is malformed or a field is out of range. `error` names every field; `issues` lists them. |
| 401 | `unauthenticated` | No API key, or one that does not work. |
| 403 | `token-scope` | The key's scopes do not cover this route. |

## POST /v1/org/signed-access/keys

Adds a signing key.

**Auth:** API key with full access (a key with scopes cannot call this route). Refused for every agent token (`agent-token-credential`).

### Request body

JSON, the shape `CreateAccessKeyRequest` of the contract.

| Field | Type | Required | Description |
| --- | --- | --- | --- |
| `label` | string | required | 1 to 64 characters. |
| `publicKey` | string | required | 1 to 1024 characters. |

### Example request

```bash
curl -X POST "https://api.rytiv.app/v1/org/signed-access/keys" \
  -H "Authorization: Bearer $RYTIV_TOKEN" \
  -H "Content-Type: application/json" \
  -d '{"label":"before-migration","publicKey":"<publicKey>"}'
```

### Response

`201` with a JSON body.

### Errors

| Status | Code | Meaning |
| --- | --- | --- |
| 400 | `bad-public-key` |  |
| 400 | `bad-request` | The request is malformed or a field is out of range. `error` names every field; `issues` lists them. |
| 400 | `private-key` |  |
| 401 | `unauthenticated` | No API key, or one that does not work. |
| 403 | `token-scope` | The key's scopes do not cover this route. |
| 409 | `duplicate-key` |  |
| 409 | `too-many-keys` |  |

## DELETE /v1/org/signed-access/keys/:id

Removes a signing key.

**Auth:** API key with full access (a key with scopes cannot call this route). Refused for every agent token (`agent-token-credential`).

### Path parameters

| Name | Description |
| --- | --- |
| `id` | The object's id. |

### Example request

```bash
curl -X DELETE "https://api.rytiv.app/v1/org/signed-access/keys/<id>" \
  -H "Authorization: Bearer $RYTIV_TOKEN"
```

### Response

`204` with no body.

### Errors

| Status | Code | Meaning |
| --- | --- | --- |
| 401 | `unauthenticated` | No API key, or one that does not work. |
| 403 | `token-scope` | The key's scopes do not cover this route. |
| 404 | `not-found` | Not found, or not yours. An object of another organization answers like one that does not exist. |

## POST /v1/orgs/managed

Creates an organization that yours manages.

**Auth:** API key with full access (a key with scopes cannot call this route). Refused for every agent token (`agent-token-credential`).

### Request body

JSON, the shape `CreateManagedOrgRequest` of the contract.

| Field | Type | Required | Description |
| --- | --- | --- | --- |
| `name` | string | required | 1 to 120 characters. |

### Example request

```bash
curl -X POST "https://api.rytiv.app/v1/orgs/managed" \
  -H "Authorization: Bearer $RYTIV_TOKEN" \
  -H "Content-Type: application/json" \
  -d '{"name":"my-app"}'
```

### Response

`200` or `201` with a JSON body.

### Errors

| Status | Code | Meaning |
| --- | --- | --- |
| 400 | `bad-request` | The request is malformed or a field is out of range. `error` names every field; `issues` lists them. |
| 401 | `unauthenticated` | No API key, or one that does not work. |
| 403 | `token-scope` | The key's scopes do not cover this route. |

## GET /v1/orgs/managed

The organizations yours manages.

**Auth:** API key with full access or the scope `read`. Refused for every agent token (`agent-token-credential`).

### Example request

```bash
curl -X GET "https://api.rytiv.app/v1/orgs/managed" \
  -H "Authorization: Bearer $RYTIV_TOKEN"
```

### Response

`200` with the list:

```json
{
  "quota": -9007199254740991,
  "used": -9007199254740991,
  "remaining": -9007199254740991,
  "orgs": [
    {
      "id": "<id>",
      "name": "my-app"
    }
  ]
}
```

| Field | Type | Present | Description |
| --- | --- | --- | --- |
| `quota` | integer | always | -9007199254740991 to 9007199254740991. |
| `used` | integer | always | -9007199254740991 to 9007199254740991. |
| `remaining` | integer | always | -9007199254740991 to 9007199254740991. |
| `orgs` | array of object | always |  |

### Errors

| Status | Code | Meaning |
| --- | --- | --- |
| 401 | `unauthenticated` | No API key, or one that does not work. |
| 403 | `token-scope` | The key's scopes do not cover this route. |

## POST /v1/orgs/managed/:id/release

Hands a managed organization over to itself; your keys stop acting in it.

**Auth:** API key with full access (a key with scopes cannot call this route). Refused for every agent token (`agent-token-credential`).

### Path parameters

| Name | Description |
| --- | --- |
| `id` | The object's id. |

### Example request

```bash
curl -X POST "https://api.rytiv.app/v1/orgs/managed/<id>/release" \
  -H "Authorization: Bearer $RYTIV_TOKEN"
```

### Response

`200` with a JSON object carrying `id`, `managedBy`, `revokedTokens`.

### Errors

| Status | Code | Meaning |
| --- | --- | --- |
| 401 | `unauthenticated` | No API key, or one that does not work. |
| 403 | `token-scope` | The key's scopes do not cover this route. |
| 404 | `not-found` | Not found, or not yours. An object of another organization answers like one that does not exist. |
