On this page
Versions
A version holds pages. Every page belongs to exactly one version, and a site's default version serves from unprefixed URLs. For the behaviour this drives, see Versions.
All endpoints require an organization API key. :site and :ver each accept a slug or an id.
List versions
GET /v1/sites/:site/versions
curl -s -H "authorization: Bearer $DOCSARY_KEY" \
"$DOCSARY_API/v1/sites/acme/versions"
{
"versions": [
{ "id": "ver_...", "slug": "2.0", "name": "2.0", "position": 0 },
{ "id": "ver_...", "slug": "1.0", "name": "1.0", "position": 1 }
],
"default_version_id": "ver_..."
}
Ordered by position, then slug. Compare default_version_id against the list to find which one is current.
Create a version
POST /v1/sites/:site/versions
curl -s -X POST "$DOCSARY_API/v1/sites/acme/versions" \
-H "authorization: Bearer $DOCSARY_KEY" \
-H "content-type: application/json" \
-d '{"slug":"2.0","name":"2.0","position":0}'
| Field | Type | Required | Notes |
|---|---|---|---|
slug |
string | yes | Must match ^[a-z0-9][a-z0-9._-]*$. Unique within the site. Becomes the URL prefix when this version is not the default. |
name |
string | no | Label shown in the version switcher and the old-version banner. Defaults to the slug. |
position |
number | no | Sort position in the version switcher and in list responses. Defaults to 0. |
{ "id": "ver_...", "slug": "2.0" }
201 on success.
The first version created on a site automatically becomes its default version. Subsequent ones do not; promote them with PATCH /v1/sites/:site and a default_version field.
Rejections
| Response | Cause |
|---|---|
400 {"error":"invalid slug"} |
Slug does not match the pattern |
400 {"error":"reserved slug"} |
Slug is one of the paths the serving router owns — assets, search, v1, robots.txt, sitemap.xml, llms.txt, llms-full.txt, manifest.webmanifest, sw.js, __api, __health, __bench |
403 with quota: "versions_per_site" |
This site's version ceiling is already reached |
409 {"error":"version slug already exists"} |
The site already has this slug |
409 {"error":"slug would shadow existing page URLs at that path"} |
Some version of this site already has a page at that path, or beneath it |
The shadowing check is what keeps version prefixes and page paths from ever colliding. If any version has a page at /next or /next/anything, a version slug of next is refused. The rule is enforced in the other direction too — an import rejects a page whose first path segment matches a version slug.
The new version appears in the switcher on every page of the site straight away.
Update a version
PATCH /v1/sites/:site/versions/:ver
| Field | Type | Notes |
|---|---|---|
slug |
string | New slug. Same pattern and reserved-word rules as creation. |
name |
string | New display label. |
position |
number | New sort position. |
curl -s -X PATCH "$DOCSARY_API/v1/sites/acme/versions/1.0" \
-H "authorization: Bearer $DOCSARY_KEY" \
-H "content-type: application/json" \
-d '{"name":"1.0 (legacy)","position":9}'
{ "ok": true }
400 {"error":"invalid or reserved slug"} for a bad slug. 404 if the site or version does not resolve. The change is live immediately.
Changing a slug changes every URL of a non-default version, and nothing is redirected automatically. Existing links to /1.0/guide/install break the moment the slug becomes legacy. Add redirects for the paths that matter, or rename before the version has an audience.
The shadow check that runs at creation is not re-run on a slug change.
Renaming with name is free — it changes only the label in the switcher and banner.
Delete a version
DELETE /v1/sites/:site/versions/:ver
curl -s -X DELETE "$DOCSARY_API/v1/sites/acme/versions/0.9" \
-H "authorization: Bearer $DOCSARY_KEY"
{ "deleted": "0.9" }
Deletes the version, all of its pages, and its search index entries. Immediate, with no undo — export first if the content matters.
If the deleted version was the site's default, the site is left with no default version. Serving falls back to the first version by position, so the site keeps working, but nothing marks a version as current until you set one. Promote a replacement:
curl -s -X PATCH "$DOCSARY_API/v1/sites/acme" \
-H "authorization: Bearer $DOCSARY_KEY" \
-H "content-type: application/json" \
-d '{"default_version":"1.0"}'
The deleted version's pages stop being served immediately.