HTTP API: documents
The 7 operations tagged documents, each with its parameters, its body and what it answers.
List documents
GET /v1/documents
List the documents this caller can see.
Parameters
workspace_id(stringornull, in query): Which workspace, by id or slug.project(stringornull, in query): Restrict to one project.type(stringornull, in query): Restrict to one document type key.status(stringornull, in query): Restrict to one status key.tag(stringornull, in query): Restrict to items carrying this tag, without the '#'. Matched however it was capitalised.status_category(stringornull, in query): Restrict to one status category: draft, current, superseded or archived. Unlike 'status' this survives an installation renaming its statuses, so it is the handle to ask which documents are in force with. A document's categories are its own — a superseded specification is not 'done'.q(stringornull, in query): Words to look for in the title or the body. Every one must appear.deleted(boolean, in query): Show *only* what is in the trash, rather than including it.order(stringornull, in query): Comma-separated sort fields.limit(integerornull, in query): How many to return. At least 1; capped at the instance's max_page_size.cursor(stringornull, in query): Continue after a previous page.include_total(boolean, in query): Count the whole result.group_by(stringornull, in query): Split the answer into groups, each with an allowance of its own, so that no group can be starved by its neighbours. 'status_category' is the one axis today. Changes the response shape: 'groups', each with 'key', 'items' and its own 'page'. Every group the axis has is present, including empty ones.group_limit(integerornull, in query): How many rows each group carries. Defaults to 25 and cannot exceed 100, because the cost of a grouped request is this times the number of groups. Only meaningful with group_by.include(stringornull, in query): Extras to return beside the items, comma-separated.linksadds alinksarray of the links among this page's items — each one{id, link_type, label, source, target}, reported once however many of its ends are on the page. Absent unless asked for, and unaffected byfields.format(stringornull, in query): 'full' (default), 'compact' for one aligned line per item, or 'ids' for the addresses alone. Compact is roughly a twentieth the size of full.fields(stringornull, in query): Comma-separated field names to return instead of the whole item, e.g. 'ref,title,due_at'. GET /v1/meta lists what each entity has. Cannot be combined with 'format'.
Responses
200:Collection_Document_. Successful Response422:HTTPValidationError. Validation Error
Write a document
POST /v1/documents
Create a document — a spec, a design, a note, a decision, a finding or a dead end.
Request body: Create as application/json, required.
Responses
201:Document. Successful Response422:HTTPValidationError. Validation Error
Read one document
GET /v1/documents/{id_or_ref}
Return one document, by id or by ref.
Parameters
id_or_ref(string, in path, required): The item's ref — a plain integer, as returned inref— or its id.42and019f…are both accepted. Write#42in prose, never in a URL.workspace_id(stringornull, in query): Which workspace, by id or slug.format(stringornull, in query): 'full' (default), 'compact' for one aligned line per item, or 'ids' for the addresses alone. Compact is roughly a twentieth the size of full.fields(stringornull, in query): Comma-separated field names to return instead of the whole item, e.g. 'ref,title,due_at'. GET /v1/meta lists what each entity has. Cannot be combined with 'format'.
Responses
200:Document. Successful Response422:HTTPValidationError. Validation Error
Change a document
PATCH /v1/documents/{id_or_ref}
Change a document. Omitted fields are untouched; nulls clear (docs/design.md §8.3).
Parameters
id_or_ref(string, in path, required): The item's ref — a plain integer, as returned inref— or its id.42and019f…are both accepted. Write#42in prose, never in a URL.workspace_id(stringornull, in query): Which workspace, by id or slug.
Request body: Update as application/json, required.
Responses
200:Document. Successful Response422:HTTPValidationError. Validation Error
Move a document to the trash
DELETE /v1/documents/{id_or_ref}
Soft-delete a document. It stays recoverable (docs/design.md §6.9).
Parameters
id_or_ref(string, in path, required): The item's ref — a plain integer, as returned inref— or its id.42and019f…are both accepted. Write#42in prose, never in a URL.workspace_id(stringornull, in query): Which workspace, by id or slug.
Responses
200:Document. Successful Response422:HTTPValidationError. Validation Error
Nest a document under another, or move it to the top level
POST /v1/documents/{id_or_ref}/move
Re-nest a document, taking its sections with it.
The half of re-parenting that had no endpoint at all. parent_id was reported by this
view and accepted nowhere — not here, not on create, not on update — so a document could
be a section of another only by being inserted into the database directly.
Parameters
id_or_ref(string, in path, required): The item's ref — a plain integer, as returned inref— or its id.42and019f…are both accepted. Write#42in prose, never in a URL.workspace_id(stringornull, in query): Which workspace, by id or slug.
Request body: Move as application/json, required.
Responses
200:Document. Successful Response422:HTTPValidationError. Validation Error
Take a document out of the trash
POST /v1/documents/{id_or_ref}/restore
Restore a soft-deleted document — the task endpoint's counterpart (docs/design.md §6.9).
Both, because one ref counter serves both kinds (§6.2): a restore that worked on half the numbers would surprise anybody holding a ref.
Parameters
id_or_ref(string, in path, required): The item's ref — a plain integer, as returned inref— or its id.42and019f…are both accepted. Write#42in prose, never in a URL.workspace_id(stringornull, in query): Which workspace, by id or slug.
Responses
200:Document. Successful Response422:HTTPValidationError. Validation Error