Kanorio

API 參考

Collections

Management API: GET /sites/{id}/collections, POST /sites/{id}/collections, GET /sites/{id}/collections/{key}, …

此頁只有英文版。API 參考、Webhook 事件及變更紀錄維持英文,與程式碼中的欄位名稱、錯誤碼一致。
Base URL https://app.kanorio.com/api/v1ErrorsPagination

List collections

GET/sites/{id}/collections
betacollections:viewdefault (120/minute per token)

List the site's collections (custom and system) with their field schemas and item counts. Call this before reading or writing items. Errors: FORBIDDEN, INVALID_CURSOR.

Parameters

  • idstring · pathrequired

    Website id. Get it from sites.list or from sites.create.

  • limitinteger · query

    Maximum number of items to return, 1–100. Defaults to 20.

  • cursorstring · query

    Opaque cursor from the previous page's nextCursor. Omit for the first page.

Response 200

  • dataobject[]required
  • data[].idstringrequired
  • data[].keystringrequired
  • data[].displayNamestringrequired
  • data[].singularNamestringrequired
  • data[].descriptionstring | nullrequired
  • data[].kind"custom" | "system"required

    system collections (blog) have reserved fields that cannot be removed or retyped.

  • data[].systemKeystring | nullrequired
  • data[].fieldsobject[]required
  • data[].fields[].idstringrequired
  • data[].fields[].namestringrequired
  • data[].fields[].requiredbooleanrequired
  • data[].fields[].helpstring
  • data[].fields[].aiHintstring
  • data[].fields[].systemboolean
  • data[].fields[].indexedboolean
  • data[].fields[].uniqueboolean
  • data[].fields[].type"text"required
  • data[].fields[].mininteger
  • data[].fields[].maxinteger
  • data[].fields[].patternstring
  • data[].fields[].defaultstring
  • data[].fields[].localizedboolean
  • data[].titleFieldIdstringrequired
  • data[].accessPolicyobject | nullrequired

    Field-level read policy for the Content Delivery API: gatedFields are stripped on anonymous requests (returning top-level access summary) and unlocked when a Customer Access Token (knr_cat_) satisfies requires (customer login or an active entitlement featureKey).

  • data[].accessPolicy.gatedFieldsstring[]required
  • data[].accessPolicy.requiresobjectrequired
  • data[].accessPolicy.itemOverrideFieldstring
  • data[].searchobject | nullrequired

    Site-search settings. null = items are not indexed. fields: text/rich_text fieldIds searched as body (the title field is always indexed). pathTemplate (optional, e.g. /recipes/{slug}) is a presentation setting: when set, search hits carry a url; otherwise url is null and the front end routes by collectionKey + slug or fetches the item from the Delivery API.

  • data[].search.fieldsstring[]required
  • data[].search.pathTemplatestring | null
  • data[].createdByobjectrequired
  • data[].createdBy.kind"agent" | "user"required
  • data[].createdBy.actorIdstringrequired
  • data[].createdBy.clientNamestring | null
  • data[].itemCountintegerrequired
  • data[].createdAtstringrequired
  • data[].updatedAtstringrequired
  • hasMorebooleanrequired

    True when another page exists; pass nextCursor to fetch it.

  • nextCursorstring | nullrequired

    Cursor for the next page, or null on the last page.

Errors

  • FORBIDDEN 403
  • INVALID_CURSOR 400

MCP tool collections_list

curl -X GET "https://app.kanorio.com/api/v1/sites/{id}/collections" \
  -H "Authorization: Bearer $KANORIO_TOKEN"
Response
{
  "data": [
    {
      "id": "coll_example01",
      "key": "teachers",
      "displayName": "Teachers",
      "singularName": "Teacher",
      "description": "Faculty shown on the About page.",
      "kind": "custom",
      "systemKey": null,
      "fields": [
        {
          "id": "name",
          "name": "Name",
          "type": "text",
          "required": true,
          "max": 80,
          "unique": true,
          "aiHint": "Full name as shown on the site."
        },
        {
          "id": "avatar",
          "name": "Avatar",
          "type": "image",
          "required": false,
          "help": "Square portrait."
        },
        {
          "id": "subjects",
          "name": "Subjects",
          "type": "multi_select",
          "required": true,
          "options": [
            {
              "id": "math",
              "label": "Math"
            },
            {
              "id": "english",
              "label": "English"
            },
            {
              "id": "physics",
              "label": "Physics"
            }
          ]
        },
        {
          "id": "bio",
          "name": "Bio",
          "type": "rich_text",
          "required": false,
          "max": 2000
        },
        {
          "id": "website",
          "name": "Personal website",
          "type": "url",
          "required": false
        },
        {
          "id": "course",
          "name": "Main course",
          "type": "reference",
          "required": false,
          "targetCollectionKey": "courses"
        }
      ],
      "titleFieldId": "name",
      "accessPolicy": null,
      "search": {
        "fields": [
          "bio"
        ]
      },
      "createdBy": {
        "kind": "agent",
        "actorId": "user_example01",
        "clientName": "Cursor"
      },
      "itemCount": 3,
      "createdAt": "2026-10-01T02:30:00.000Z",
      "updatedAt": "2026-10-06T08:00:00.000Z"
    },
    {
      "id": "coll_example02",
      "key": "courses",
      "displayName": "Courses",
      "singularName": "Course",
      "description": null,
      "kind": "custom",
      "systemKey": null,
      "fields": [
        {
          "id": "name",
          "name": "Name",
          "type": "text",
          "required": true
        }
      ],
      "titleFieldId": "name",
      "accessPolicy": null,
      "search": null,
      "createdBy": {
        "kind": "agent",
        "actorId": "user_example01",
        "clientName": "Cursor"
      },
      "itemCount": 2,
      "createdAt": "2026-10-01T02:30:00.000Z",
      "updatedAt": "2026-10-06T08:00:00.000Z"
    }
  ],
  "hasMore": false,
  "nextCursor": null
}

Create a collection

POST/sites/{id}/collections
betacollections:schemadefault (120/minute per token)

Create a collection (a small database for site content: teachers, projects, locations, FAQ…). Not for app data such as members, orders or comments. Field types: text, rich_text, email, phone, url, video_url, number, boolean, date, datetime, select, multi_select, color, image, gallery, file, reference, multi_reference, json. Every field needs id (snake_case), name, type; required defaults to false. Constraints: text min/max/pattern/unique/default; number integer/min/max/unique; select/multi_select options [{id,label}]; reference/multi_reference targetCollectionKey; gallery/multi_* max. Add aiHint to tell future agents how to fill a field. titleFieldId must point to a text/email/url field; it names items and generates slugs. Optional search: { fields, pathTemplate? } puts published items into site search (GET /api/v1/search returns kind=COLLECTION_ITEM, collectionKey, refId, slug; url only when pathTemplate is set). Returns the Delivery API endpoints and a fetch example. Errors: FORBIDDEN, VALIDATION (details.issues), KEY_TAKEN, COLLECTION_LIMIT_REACHED, SYSTEM_COLLECTION (reserved key).

Parameters

  • idstring · pathrequired

    Website id. Get it from sites.list or from sites.create.

Request body

  • keystringrequired
  • displayNamestringrequired
  • singularNamestringrequired
  • descriptionstring
  • fieldsobject[]required
  • fields[].idstringrequired
  • fields[].namestringrequired
  • fields[].requiredboolean
  • fields[].helpstring
  • fields[].aiHintstring
  • fields[].systemboolean
  • fields[].indexedboolean
  • fields[].uniqueboolean
  • fields[].type"text"required
  • fields[].mininteger
  • fields[].maxinteger
  • fields[].patternstring
  • fields[].defaultstring
  • fields[].localizedboolean
  • titleFieldIdstringrequired
  • accessPolicyobject | null
  • accessPolicy.gatedFieldsstring[]required
  • accessPolicy.requiresobjectrequired
  • accessPolicy.requires.kind"customer"required
  • accessPolicy.itemOverrideFieldstring
  • searchobject | null
  • search.fieldsstring[]required
  • search.pathTemplatestring | null

Response 201

  • collectionobjectrequired
  • collection.idstringrequired
  • collection.keystringrequired
  • collection.displayNamestringrequired
  • collection.singularNamestringrequired
  • collection.descriptionstring | nullrequired
  • collection.kind"custom" | "system"required

    system collections (blog) have reserved fields that cannot be removed or retyped.

  • collection.systemKeystring | nullrequired
  • collection.fieldsobject[]required
  • collection.fields[].idstringrequired
  • collection.fields[].namestringrequired
  • collection.fields[].requiredbooleanrequired
  • collection.fields[].helpstring
  • collection.fields[].aiHintstring
  • collection.fields[].systemboolean
  • collection.fields[].indexedboolean
  • collection.fields[].uniqueboolean
  • collection.fields[].type"text"required
  • collection.fields[].mininteger
  • collection.fields[].maxinteger
  • collection.fields[].patternstring
  • collection.fields[].defaultstring
  • collection.fields[].localizedboolean
  • collection.titleFieldIdstringrequired
  • collection.accessPolicyobject | nullrequired

    Field-level read policy for the Content Delivery API: gatedFields are stripped on anonymous requests (returning top-level access summary) and unlocked when a Customer Access Token (knr_cat_) satisfies requires (customer login or an active entitlement featureKey).

  • collection.accessPolicy.gatedFieldsstring[]required
  • collection.accessPolicy.requiresobjectrequired
  • collection.accessPolicy.itemOverrideFieldstring
  • collection.searchobject | nullrequired

    Site-search settings. null = items are not indexed. fields: text/rich_text fieldIds searched as body (the title field is always indexed). pathTemplate (optional, e.g. /recipes/{slug}) is a presentation setting: when set, search hits carry a url; otherwise url is null and the front end routes by collectionKey + slug or fetches the item from the Delivery API.

  • collection.search.fieldsstring[]required
  • collection.search.pathTemplatestring | null
  • collection.createdByobjectrequired
  • collection.createdBy.kind"agent" | "user"required
  • collection.createdBy.actorIdstringrequired
  • collection.createdBy.clientNamestring | null
  • collection.itemCountintegerrequired
  • collection.createdAtstringrequired
  • collection.updatedAtstringrequired
  • deliveryobjectrequired
  • delivery.baseUrlstringrequired

    The site's public origin.

  • delivery.listUrlstringrequired
  • delivery.itemUrlstringrequired

    Replace {slug} with an item's slug.

  • delivery.schemaUrlstringrequired
  • delivery.fetchExamplestringrequired

    Copy-paste JavaScript using fetch().

  • delivery.corsstringrequired

    How cross-origin access works and where to allow origins.

Errors

  • FORBIDDEN 403
  • VALIDATION 400 · details.issues
  • KEY_TAKEN 409
  • COLLECTION_LIMIT_REACHED 403
  • SYSTEM_COLLECTION 409 · reserved key

MCP tool collections_create

curl -X POST "https://app.kanorio.com/api/v1/sites/{id}/collections" \
  -H "Authorization: Bearer $KANORIO_TOKEN" \
  -H "Content-Type: application/json" \
  -d '{"key":"teachers","displayName":"Teachers","singularName":"Teacher","description":"Faculty shown on the About page.","titleFieldId":"name","fields":[{"id":"name","name":"Name","type":"text","required":true,"max":80,"unique":true,"aiHint":"Full name as shown on the site."},{"id":"avatar","name":"Avatar","type":"image","required":false,"help":"Square portrait."},{"id":"subjects","name":"Subjects","type":"multi_select","required":true,"options":[{"id":"math","label":"Math"},{"id":"english","label":"English"},{"id":"physics","label":"Physics"}]},{"id":"bio","name":"Bio","type":"rich_text","required":false,"max":2000},{"id":"website","name":"Personal website","type":"url","required":false},{"id":"course","name":"Main course","type":"reference","required":false,"targetCollectionKey":"courses"}]}'
Response
{
  "collection": {
    "id": "coll_example01",
    "key": "teachers",
    "displayName": "Teachers",
    "singularName": "Teacher",
    "description": "Faculty shown on the About page.",
    "kind": "custom",
    "systemKey": null,
    "fields": [
      {
        "id": "name",
        "name": "Name",
        "type": "text",
        "required": true,
        "max": 80,
        "unique": true,
        "aiHint": "Full name as shown on the site."
      },
      {
        "id": "avatar",
        "name": "Avatar",
        "type": "image",
        "required": false,
        "help": "Square portrait."
      },
      {
        "id": "subjects",
        "name": "Subjects",
        "type": "multi_select",
        "required": true,
        "options": [
          {
            "id": "math",
            "label": "Math"
          },
          {
            "id": "english",
            "label": "English"
          },
          {
            "id": "physics",
            "label": "Physics"
          }
        ]
      },
      {
        "id": "bio",
        "name": "Bio",
        "type": "rich_text",
        "required": false,
        "max": 2000
      },
      {
        "id": "website",
        "name": "Personal website",
        "type": "url",
        "required": false
      },
      {
        "id": "course",
        "name": "Main course",
        "type": "reference",
        "required": false,
        "targetCollectionKey": "courses"
      }
    ],
    "titleFieldId": "name",
    "accessPolicy": null,
    "search": {
      "fields": [
        "bio"
      ]
    },
    "createdBy": {
      "kind": "agent",
      "actorId": "user_example01",
      "clientName": "Cursor"
    },
    "itemCount": 0,
    "createdAt": "2026-10-01T02:30:00.000Z",
    "updatedAt": "2026-10-06T08:00:00.000Z"
  },
  "delivery": {
    "baseUrl": "https://sunny-bakery.kanorio.com",
    "listUrl": "https://sunny-bakery.kanorio.com/api/v1/collections/teachers/items",
    "itemUrl": "https://sunny-bakery.kanorio.com/api/v1/collections/teachers/items/{slug}",
    "schemaUrl": "https://sunny-bakery.kanorio.com/api/v1/collections",
    "fetchExample": "const res = await fetch(\"https://sunny-bakery.kanorio.com/api/v1/collections/teachers/items?limit=20&sort=-publishedAt\");\nconst { data, hasMore, nextCursor } = await res.json();",
    "cors": "Same-origin requests need no setup. Other origins must be added with site.update_allowed_origins; localhost is always allowed."
  }
}

Retrieve a collection

GET/sites/{id}/collections/{key}
betacollections:viewdefault (120/minute per token)

Get one collection's schema (fields, constraints, aiHint) plus its Content Delivery API endpoints. Errors: FORBIDDEN, COLLECTION_NOT_FOUND.

Parameters

  • idstring · pathrequired

    Website id. Get it from sites.list or from sites.create.

  • keystring · pathrequired

    Collection key (slug). Get it from collections.list.

Response 200

  • collectionobjectrequired
  • collection.idstringrequired
  • collection.keystringrequired
  • collection.displayNamestringrequired
  • collection.singularNamestringrequired
  • collection.descriptionstring | nullrequired
  • collection.kind"custom" | "system"required

    system collections (blog) have reserved fields that cannot be removed or retyped.

  • collection.systemKeystring | nullrequired
  • collection.fieldsobject[]required
  • collection.fields[].idstringrequired
  • collection.fields[].namestringrequired
  • collection.fields[].requiredbooleanrequired
  • collection.fields[].helpstring
  • collection.fields[].aiHintstring
  • collection.fields[].systemboolean
  • collection.fields[].indexedboolean
  • collection.fields[].uniqueboolean
  • collection.fields[].type"text"required
  • collection.fields[].mininteger
  • collection.fields[].maxinteger
  • collection.fields[].patternstring
  • collection.fields[].defaultstring
  • collection.fields[].localizedboolean
  • collection.titleFieldIdstringrequired
  • collection.accessPolicyobject | nullrequired

    Field-level read policy for the Content Delivery API: gatedFields are stripped on anonymous requests (returning top-level access summary) and unlocked when a Customer Access Token (knr_cat_) satisfies requires (customer login or an active entitlement featureKey).

  • collection.accessPolicy.gatedFieldsstring[]required
  • collection.accessPolicy.requiresobjectrequired
  • collection.accessPolicy.itemOverrideFieldstring
  • collection.searchobject | nullrequired

    Site-search settings. null = items are not indexed. fields: text/rich_text fieldIds searched as body (the title field is always indexed). pathTemplate (optional, e.g. /recipes/{slug}) is a presentation setting: when set, search hits carry a url; otherwise url is null and the front end routes by collectionKey + slug or fetches the item from the Delivery API.

  • collection.search.fieldsstring[]required
  • collection.search.pathTemplatestring | null
  • collection.createdByobjectrequired
  • collection.createdBy.kind"agent" | "user"required
  • collection.createdBy.actorIdstringrequired
  • collection.createdBy.clientNamestring | null
  • collection.itemCountintegerrequired
  • collection.createdAtstringrequired
  • collection.updatedAtstringrequired
  • deliveryobjectrequired
  • delivery.baseUrlstringrequired

    The site's public origin.

  • delivery.listUrlstringrequired
  • delivery.itemUrlstringrequired

    Replace {slug} with an item's slug.

  • delivery.schemaUrlstringrequired
  • delivery.fetchExamplestringrequired

    Copy-paste JavaScript using fetch().

  • delivery.corsstringrequired

    How cross-origin access works and where to allow origins.

Errors

  • FORBIDDEN 403
  • COLLECTION_NOT_FOUND 404

MCP tool collections_get

curl -X GET "https://app.kanorio.com/api/v1/sites/{id}/collections/{key}" \
  -H "Authorization: Bearer $KANORIO_TOKEN"
Response
{
  "collection": {
    "id": "coll_example01",
    "key": "teachers",
    "displayName": "Teachers",
    "singularName": "Teacher",
    "description": "Faculty shown on the About page.",
    "kind": "custom",
    "systemKey": null,
    "fields": [
      {
        "id": "name",
        "name": "Name",
        "type": "text",
        "required": true,
        "max": 80,
        "unique": true,
        "aiHint": "Full name as shown on the site."
      },
      {
        "id": "avatar",
        "name": "Avatar",
        "type": "image",
        "required": false,
        "help": "Square portrait."
      },
      {
        "id": "subjects",
        "name": "Subjects",
        "type": "multi_select",
        "required": true,
        "options": [
          {
            "id": "math",
            "label": "Math"
          },
          {
            "id": "english",
            "label": "English"
          },
          {
            "id": "physics",
            "label": "Physics"
          }
        ]
      },
      {
        "id": "bio",
        "name": "Bio",
        "type": "rich_text",
        "required": false,
        "max": 2000
      },
      {
        "id": "website",
        "name": "Personal website",
        "type": "url",
        "required": false
      },
      {
        "id": "course",
        "name": "Main course",
        "type": "reference",
        "required": false,
        "targetCollectionKey": "courses"
      }
    ],
    "titleFieldId": "name",
    "accessPolicy": null,
    "search": {
      "fields": [
        "bio"
      ]
    },
    "createdBy": {
      "kind": "agent",
      "actorId": "user_example01",
      "clientName": "Cursor"
    },
    "itemCount": 3,
    "createdAt": "2026-10-01T02:30:00.000Z",
    "updatedAt": "2026-10-06T08:00:00.000Z"
  },
  "delivery": {
    "baseUrl": "https://sunny-bakery.kanorio.com",
    "listUrl": "https://sunny-bakery.kanorio.com/api/v1/collections/teachers/items",
    "itemUrl": "https://sunny-bakery.kanorio.com/api/v1/collections/teachers/items/{slug}",
    "schemaUrl": "https://sunny-bakery.kanorio.com/api/v1/collections",
    "fetchExample": "const res = await fetch(\"https://sunny-bakery.kanorio.com/api/v1/collections/teachers/items?limit=20&sort=-publishedAt\");\nconst { data, hasMore, nextCursor } = await res.json();",
    "cors": "Same-origin requests need no setup. Other origins must be added with site.update_allowed_origins; localhost is always allowed."
  }
}

Update a collection

PATCH/sites/{id}/collections/{key}
betacollections:schemadefault (120/minute per token)

Change a collection's name, description, titleFieldId, fields, accessPolicy or search. fields replaces the whole ordered list: read it with collections.get, edit, send it back. Allowed immediately: add fields, rename, change help/aiHint, add options, relax constraints, remove custom fields (data is ignored, cleaned on next write). Type changes only along compatible paths (e.g. text→rich_text, select→multi_select, reference→multi_reference, image→gallery); otherwise add a new field, migrate, remove the old one. Tightened constraints are checked against existing items first. accessPolicy gates specific fieldIds (e.g. blog content) behind customer sign-in ({ kind: "customer" }) or an active commercial entitlement ({ kind: "entitlement", featureKey: "premium" }), with optional itemOverrideField (select field with public/customer/paid); pass null to clear. System collections (blog): reserved fields cannot be removed or retyped, but accessPolicy and custom fields can be configured. Errors: FORBIDDEN, COLLECTION_NOT_FOUND, VALIDATION (details.issues), SCHEMA_CHANGE_REJECTED (details.schemaIssues).

Parameters

  • idstring · pathrequired

    Website id. Get it from sites.list or from sites.create.

  • keystring · pathrequired

    Collection key (slug). Get it from collections.list.

Request body

  • displayNamestring
  • singularNamestring
  • descriptionstring | null
  • fieldsobject[]
  • fields[].idstringrequired
  • fields[].namestringrequired
  • fields[].requiredboolean
  • fields[].helpstring
  • fields[].aiHintstring
  • fields[].systemboolean
  • fields[].indexedboolean
  • fields[].uniqueboolean
  • fields[].type"text"required
  • fields[].mininteger
  • fields[].maxinteger
  • fields[].patternstring
  • fields[].defaultstring
  • fields[].localizedboolean
  • titleFieldIdstring
  • accessPolicyobject | null

    Field-level read policy (gatedFields, requires: customer | entitlement(featureKey), optional itemOverrideField). Pass null to remove the policy.

  • accessPolicy.gatedFieldsstring[]required
  • accessPolicy.requiresobjectrequired
  • accessPolicy.requires.kind"customer"required
  • accessPolicy.itemOverrideFieldstring
  • searchobject | null

    Site-search settings: { fields: [text/rich_text fieldIds], pathTemplate?: '/recipes/{slug}' }. Gated fields cannot be searched. Pass null to remove the collection from site search. Not configurable on system collections.

  • search.fieldsstring[]required
  • search.pathTemplatestring | null

Response 200

  • collectionobjectrequired
  • collection.idstringrequired
  • collection.keystringrequired
  • collection.displayNamestringrequired
  • collection.singularNamestringrequired
  • collection.descriptionstring | nullrequired
  • collection.kind"custom" | "system"required

    system collections (blog) have reserved fields that cannot be removed or retyped.

  • collection.systemKeystring | nullrequired
  • collection.fieldsobject[]required
  • collection.fields[].idstringrequired
  • collection.fields[].namestringrequired
  • collection.fields[].requiredbooleanrequired
  • collection.fields[].helpstring
  • collection.fields[].aiHintstring
  • collection.fields[].systemboolean
  • collection.fields[].indexedboolean
  • collection.fields[].uniqueboolean
  • collection.fields[].type"text"required
  • collection.fields[].mininteger
  • collection.fields[].maxinteger
  • collection.fields[].patternstring
  • collection.fields[].defaultstring
  • collection.fields[].localizedboolean
  • collection.titleFieldIdstringrequired
  • collection.accessPolicyobject | nullrequired

    Field-level read policy for the Content Delivery API: gatedFields are stripped on anonymous requests (returning top-level access summary) and unlocked when a Customer Access Token (knr_cat_) satisfies requires (customer login or an active entitlement featureKey).

  • collection.accessPolicy.gatedFieldsstring[]required
  • collection.accessPolicy.requiresobjectrequired
  • collection.accessPolicy.itemOverrideFieldstring
  • collection.searchobject | nullrequired

    Site-search settings. null = items are not indexed. fields: text/rich_text fieldIds searched as body (the title field is always indexed). pathTemplate (optional, e.g. /recipes/{slug}) is a presentation setting: when set, search hits carry a url; otherwise url is null and the front end routes by collectionKey + slug or fetches the item from the Delivery API.

  • collection.search.fieldsstring[]required
  • collection.search.pathTemplatestring | null
  • collection.createdByobjectrequired
  • collection.createdBy.kind"agent" | "user"required
  • collection.createdBy.actorIdstringrequired
  • collection.createdBy.clientNamestring | null
  • collection.itemCountintegerrequired
  • collection.createdAtstringrequired
  • collection.updatedAtstringrequired

Errors

  • FORBIDDEN 403
  • COLLECTION_NOT_FOUND 404
  • VALIDATION 400 · details.issues
  • SCHEMA_CHANGE_REJECTED 422 · details.schemaIssues

MCP tool collections_update

curl -X PATCH "https://app.kanorio.com/api/v1/sites/{id}/collections/{key}" \
  -H "Authorization: Bearer $KANORIO_TOKEN" \
  -H "Content-Type: application/json" \
  -d '{"description":"Faculty and guest lecturers.","fields":[{"id":"name","name":"Name","type":"text","required":true,"max":80,"unique":true,"aiHint":"Full name as shown on the site."},{"id":"avatar","name":"Avatar","type":"image","required":false,"help":"Square portrait."},{"id":"subjects","name":"Subjects","type":"multi_select","required":true,"options":[{"id":"math","label":"Math"},{"id":"english","label":"English"},{"id":"physics","label":"Physics"}]},{"id":"bio","name":"Bio","type":"rich_text","required":false,"max":2000},{"id":"website","name":"Personal website","type":"url","required":false},{"id":"course","name":"Main course","type":"reference","required":false,"targetCollectionKey":"courses"},{"id":"years","name":"Years of experience","type":"number","required":false,"integer":true,"min":0}]}'
Response
{
  "collection": {
    "id": "coll_example01",
    "key": "teachers",
    "displayName": "Teachers",
    "singularName": "Teacher",
    "description": "Faculty and guest lecturers.",
    "kind": "custom",
    "systemKey": null,
    "fields": [
      {
        "id": "name",
        "name": "Name",
        "type": "text",
        "required": true,
        "max": 80,
        "unique": true,
        "aiHint": "Full name as shown on the site."
      },
      {
        "id": "avatar",
        "name": "Avatar",
        "type": "image",
        "required": false,
        "help": "Square portrait."
      },
      {
        "id": "subjects",
        "name": "Subjects",
        "type": "multi_select",
        "required": true,
        "options": [
          {
            "id": "math",
            "label": "Math"
          },
          {
            "id": "english",
            "label": "English"
          },
          {
            "id": "physics",
            "label": "Physics"
          }
        ]
      },
      {
        "id": "bio",
        "name": "Bio",
        "type": "rich_text",
        "required": false,
        "max": 2000
      },
      {
        "id": "website",
        "name": "Personal website",
        "type": "url",
        "required": false
      },
      {
        "id": "course",
        "name": "Main course",
        "type": "reference",
        "required": false,
        "targetCollectionKey": "courses"
      }
    ],
    "titleFieldId": "name",
    "accessPolicy": null,
    "search": {
      "fields": [
        "bio"
      ]
    },
    "createdBy": {
      "kind": "agent",
      "actorId": "user_example01",
      "clientName": "Cursor"
    },
    "itemCount": 3,
    "createdAt": "2026-10-01T02:30:00.000Z",
    "updatedAt": "2026-10-06T08:00:00.000Z"
  }
}

Delete a collection

DELETE/sites/{id}/collections/{key}
betacollections:schemadefault (120/minute per token)

Delete a custom collection and ALL its items. Irreversible. confirmKey must equal key. Refused while another collection references it, and for system collections. Not included in any OAuth scope preset; a PAT must grant collections:manage explicitly. Errors: FORBIDDEN, COLLECTION_NOT_FOUND, CONFIRM_REQUIRED, REFERENCED (details.referencedBy), SYSTEM_COLLECTION.

Parameters

  • idstring · pathrequired

    Website id. Get it from sites.list or from sites.create.

  • keystring · pathrequired

    Collection key (slug). Get it from collections.list.

  • confirmKeystring · queryrequired

    Must equal key.

Response 200

  • deletedItemsintegerrequired

Errors

  • FORBIDDEN 403
  • COLLECTION_NOT_FOUND 404
  • CONFIRM_REQUIRED 400
  • REFERENCED 409 · details.referencedBy
  • SYSTEM_COLLECTION 409

MCP tool collections_delete

curl -X DELETE "https://app.kanorio.com/api/v1/sites/{id}/collections/{key}?confirmKey=teachers" \
  -H "Authorization: Bearer $KANORIO_TOKEN"
Response
{
  "deletedItems": 3
}