Skip to content
UpVoiced Docs

API reference

Boards

Feedback boards, their visibility and order.

Set up the SDK client used in the examples

API key or Dashboard session:

import { UpVoiced } from '@upvoiced/sdk';

const apiKey = process.env['UPVOICED_API_KEY']; // uv_live_… (Settings → API keys)
const workspace = process.env['UPVOICED_WORKSPACE_ID']; // sent as X-Workspace
if (!apiKey || !workspace) throw new Error('Set UPVOICED_API_KEY and UPVOICED_WORKSPACE_ID.');
const upvoiced = new UpVoiced({ apiKey, workspace });

curl examples read $UPVOICED_API_KEY and $UPVOICED_WORKSPACE_IDfrom your shell. MCP examples are the tools/call request an MCP client sends to the MCP server with the same API key.

GET/v1/boards

List boards, including private, unlisted and archived ones (any member)

Authentication
API key or Dashboard session; API key scope read
Operation id
listBoards
Headers
NameTypeRequired
x-workspacestring (uuid)Yes
Response 200: 16 fields
Response 200 (application/json)
NameTypeRequired
itemsarray of objectYes
items[].idstring (uuid)Yes
items[].workspace_idstring (uuid)Yes
items[].namestringlength 1–100Yes
items[].slugstringlength 3–32pattern ^[a-z0-9][a-z0-9-]*[a-z0-9]$Yes
items[].descriptionstringlength ≤ 2000Yes
items[].visibility"public" | "private" | "unlisted"Yes
items[].require_approvalbooleanYes
items[].anonymous_votingbooleanYes
items[].multi_votebooleanYes
items[].show_on_roadmapbooleanYes
items[].positionintegervalue ≥ 0Yes
items[].archived_atstring (date-time) | nullYes
items[].created_atstring (date-time)Yes
items[].updated_atstring (date-time)Yes
next_cursornullYes

Errors: 400, 401, 403, 404, 409, 413, 422, 429, 500, 503, all in the standard error shape.

curl
curl 'https://api.upvoiced.com/v1/boards' \
  -H "Authorization: Bearer $UPVOICED_API_KEY" \
  -H "X-Workspace: $UPVOICED_WORKSPACE_ID"
TypeScript SDK
const data = await upvoiced.get('/v1/boards');
MCP
{
  "jsonrpc": "2.0",
  "id": 1,
  "method": "tools/call",
  "params": {
    "name": "list_boards",
    "arguments": {
      "workspace": "0190f5e2-4c1d-7a3b-8c2d-5e6f7a8b9c0d"
    }
  }
}

Tool list_boards.

POST/v1/boards

Create a board; boards.max and private_boards entitlements (owner/admin)

Authentication
API key or Dashboard session; API key scope admin
Operation id
createBoard
Idempotency
Send an Idempotency-Key to make retries safe.
Headers
NameTypeRequired
x-workspacestring (uuid)Yes
idempotency-keystringpattern ^[A-Za-z0-9_.:-]{8,128}$No
Request body (JSON)
NameTypeRequired
namestringlength 1–100Yes
slugstringlength 3–32pattern ^[a-z0-9][a-z0-9-]*[a-z0-9]$Yes
descriptionstringlength ≤ 2000default ""No
visibility"public" | "private" | "unlisted"default "public"No
require_approvalbooleandefault falseNo
anonymous_votingbooleandefault falseNo
multi_votebooleandefault falseNo
show_on_roadmapbooleandefault trueNo
Response 201: 14 fields
Response 201 (application/json)
NameTypeRequired
idstring (uuid)Yes
workspace_idstring (uuid)Yes
namestringlength 1–100Yes
slugstringlength 3–32pattern ^[a-z0-9][a-z0-9-]*[a-z0-9]$Yes
descriptionstringlength ≤ 2000Yes
visibility"public" | "private" | "unlisted"Yes
require_approvalbooleanYes
anonymous_votingbooleanYes
multi_votebooleanYes
show_on_roadmapbooleanYes
positionintegervalue ≥ 0Yes
archived_atstring (date-time) | nullYes
created_atstring (date-time)Yes
updated_atstring (date-time)Yes

Errors: 400, 401, 403, 404, 409, 413, 422, 429, 500, 503, all in the standard error shape.

curl
curl -X POST 'https://api.upvoiced.com/v1/boards' \
  -H "Authorization: Bearer $UPVOICED_API_KEY" \
  -H "X-Workspace: $UPVOICED_WORKSPACE_ID" \
  -H "Idempotency-Key: $(uuidgen)" \
  -H "Content-Type: application/json" \
  -d '{
  "name": "Example",
  "slug": "dark-mode"
}'
TypeScript SDK
const data = await upvoiced.post('/v1/boards', { body: { name: 'Example', slug: 'dark-mode' } });
MCP

No MCP tool for this operation. The MCP server covers the everyday reads and writes.

POST/v1/boards/reorder

Set the board order; ids must list every board exactly once (owner/admin)

Authentication
API key or Dashboard session; API key scope admin
Operation id
reorderBoards
Idempotency
Send an Idempotency-Key to make retries safe.
Headers
NameTypeRequired
x-workspacestring (uuid)Yes
idempotency-keystringpattern ^[A-Za-z0-9_.:-]{8,128}$No
Request body (JSON)
NameTypeRequired
idsarray of string (uuid)items 1–200Yes
Response 200: 16 fields
Response 200 (application/json)
NameTypeRequired
itemsarray of objectYes
items[].idstring (uuid)Yes
items[].workspace_idstring (uuid)Yes
items[].namestringlength 1–100Yes
items[].slugstringlength 3–32pattern ^[a-z0-9][a-z0-9-]*[a-z0-9]$Yes
items[].descriptionstringlength ≤ 2000Yes
items[].visibility"public" | "private" | "unlisted"Yes
items[].require_approvalbooleanYes
items[].anonymous_votingbooleanYes
items[].multi_votebooleanYes
items[].show_on_roadmapbooleanYes
items[].positionintegervalue ≥ 0Yes
items[].archived_atstring (date-time) | nullYes
items[].created_atstring (date-time)Yes
items[].updated_atstring (date-time)Yes
next_cursornullYes

Errors: 400, 401, 403, 404, 409, 413, 422, 429, 500, 503, all in the standard error shape.

curl
curl -X POST 'https://api.upvoiced.com/v1/boards/reorder' \
  -H "Authorization: Bearer $UPVOICED_API_KEY" \
  -H "X-Workspace: $UPVOICED_WORKSPACE_ID" \
  -H "Idempotency-Key: $(uuidgen)" \
  -H "Content-Type: application/json" \
  -d '{
  "ids": [
    "0190f5e2-4c1d-7a3b-8c2d-5e6f7a8b9c0d"
  ]
}'
TypeScript SDK
const data = await upvoiced.post('/v1/boards/reorder', { body: { ids: ['0190f5e2-4c1d-7a3b-8c2d-5e6f7a8b9c0d'] } });
MCP

No MCP tool for this operation. The MCP server covers the everyday reads and writes.

POST/v1/boards/plan-selection

Choose which active boards stay active within boards.max; the rest are read-only and hidden from public surfaces (owner/admin)

Authentication
API key or Dashboard session; API key scope admin
Operation id
selectPlanBoards
Idempotency
Send an Idempotency-Key to make retries safe.
Headers
NameTypeRequired
x-workspacestring (uuid)Yes
idempotency-keystringpattern ^[A-Za-z0-9_.:-]{8,128}$No
Request body (JSON)
NameTypeRequired
board_idsarray of string (uuid)items 1–100Yes
Response 200: 2 fields
Response 200 (application/json)
NameTypeRequired
active_board_idsarray of string (uuid)Yes
read_only_board_idsarray of string (uuid)Yes

Errors: 400, 401, 403, 404, 409, 413, 422, 429, 500, 503, all in the standard error shape.

curl
curl -X POST 'https://api.upvoiced.com/v1/boards/plan-selection' \
  -H "Authorization: Bearer $UPVOICED_API_KEY" \
  -H "X-Workspace: $UPVOICED_WORKSPACE_ID" \
  -H "Idempotency-Key: $(uuidgen)" \
  -H "Content-Type: application/json" \
  -d '{
  "board_ids": [
    "0190f5e2-4c1d-7a3b-8c2d-5e6f7a8b9c0d"
  ]
}'
TypeScript SDK
const data = await upvoiced.post('/v1/boards/plan-selection', {
  body: { board_ids: ['0190f5e2-4c1d-7a3b-8c2d-5e6f7a8b9c0d'] },
});
MCP

No MCP tool for this operation. The MCP server covers the everyday reads and writes.

GET/v1/boards/{id}

Get a board (any member)

Authentication
API key or Dashboard session; API key scope read
Operation id
getBoard
Path parameters
NameTypeRequired
idstring (uuid)Yes
Headers
NameTypeRequired
x-workspacestring (uuid)Yes
Response 200: 14 fields
Response 200 (application/json)
NameTypeRequired
idstring (uuid)Yes
workspace_idstring (uuid)Yes
namestringlength 1–100Yes
slugstringlength 3–32pattern ^[a-z0-9][a-z0-9-]*[a-z0-9]$Yes
descriptionstringlength ≤ 2000Yes
visibility"public" | "private" | "unlisted"Yes
require_approvalbooleanYes
anonymous_votingbooleanYes
multi_votebooleanYes
show_on_roadmapbooleanYes
positionintegervalue ≥ 0Yes
archived_atstring (date-time) | nullYes
created_atstring (date-time)Yes
updated_atstring (date-time)Yes

Errors: 400, 401, 403, 404, 409, 413, 422, 429, 500, 503, all in the standard error shape.

curl
curl 'https://api.upvoiced.com/v1/boards/0190f5e2-4c1d-7a3b-8c2d-5e6f7a8b9c0d' \
  -H "Authorization: Bearer $UPVOICED_API_KEY" \
  -H "X-Workspace: $UPVOICED_WORKSPACE_ID"
TypeScript SDK
const data = await upvoiced.get('/v1/boards/{id}', { path: { id: '0190f5e2-4c1d-7a3b-8c2d-5e6f7a8b9c0d' } });
MCP

No MCP tool for this operation. The MCP server covers the everyday reads and writes.

PATCH/v1/boards/{id}

Update board settings and visibility; purges cache tags (owner/admin)

Authentication
API key or Dashboard session; API key scope admin
Operation id
updateBoard
Path parameters
NameTypeRequired
idstring (uuid)Yes
Headers
NameTypeRequired
x-workspacestring (uuid)Yes
Request body (JSON)
NameTypeRequired
namestringlength 1–100No
slugstringlength 3–32pattern ^[a-z0-9][a-z0-9-]*[a-z0-9]$No
descriptionstringlength ≤ 2000No
visibility"public" | "private" | "unlisted"No
require_approvalbooleanNo
anonymous_votingbooleanNo
multi_votebooleanNo
show_on_roadmapbooleanNo
Response 200: 14 fields
Response 200 (application/json)
NameTypeRequired
idstring (uuid)Yes
workspace_idstring (uuid)Yes
namestringlength 1–100Yes
slugstringlength 3–32pattern ^[a-z0-9][a-z0-9-]*[a-z0-9]$Yes
descriptionstringlength ≤ 2000Yes
visibility"public" | "private" | "unlisted"Yes
require_approvalbooleanYes
anonymous_votingbooleanYes
multi_votebooleanYes
show_on_roadmapbooleanYes
positionintegervalue ≥ 0Yes
archived_atstring (date-time) | nullYes
created_atstring (date-time)Yes
updated_atstring (date-time)Yes

Errors: 400, 401, 403, 404, 409, 413, 422, 429, 500, 503, all in the standard error shape.

curl
curl -X PATCH 'https://api.upvoiced.com/v1/boards/0190f5e2-4c1d-7a3b-8c2d-5e6f7a8b9c0d' \
  -H "Authorization: Bearer $UPVOICED_API_KEY" \
  -H "X-Workspace: $UPVOICED_WORKSPACE_ID" \
  -H "Content-Type: application/json" \
  -d '{
  "name": "Example"
}'
TypeScript SDK
const data = await upvoiced.patch('/v1/boards/{id}', {
  path: { id: '0190f5e2-4c1d-7a3b-8c2d-5e6f7a8b9c0d' },
  body: { name: 'Example' },
});
MCP

No MCP tool for this operation. The MCP server covers the everyday reads and writes.

DELETE/v1/boards/{id}

Archive a board (reversible, keeps posts); never the last active board (owner/admin)

Authentication
API key or Dashboard session; API key scope admin
Operation id
archiveBoard
Path parameters
NameTypeRequired
idstring (uuid)Yes
Headers
NameTypeRequired
x-workspacestring (uuid)Yes
Response 200: 14 fields
Response 200 (application/json)
NameTypeRequired
idstring (uuid)Yes
workspace_idstring (uuid)Yes
namestringlength 1–100Yes
slugstringlength 3–32pattern ^[a-z0-9][a-z0-9-]*[a-z0-9]$Yes
descriptionstringlength ≤ 2000Yes
visibility"public" | "private" | "unlisted"Yes
require_approvalbooleanYes
anonymous_votingbooleanYes
multi_votebooleanYes
show_on_roadmapbooleanYes
positionintegervalue ≥ 0Yes
archived_atstring (date-time) | nullYes
created_atstring (date-time)Yes
updated_atstring (date-time)Yes

Errors: 400, 401, 403, 404, 409, 413, 422, 429, 500, 503, all in the standard error shape.

curl
curl -X DELETE 'https://api.upvoiced.com/v1/boards/0190f5e2-4c1d-7a3b-8c2d-5e6f7a8b9c0d' \
  -H "Authorization: Bearer $UPVOICED_API_KEY" \
  -H "X-Workspace: $UPVOICED_WORKSPACE_ID"
TypeScript SDK
const data = await upvoiced.delete('/v1/boards/{id}', { path: { id: '0190f5e2-4c1d-7a3b-8c2d-5e6f7a8b9c0d' } });
MCP

No MCP tool for this operation. The MCP server covers the everyday reads and writes.

POST/v1/boards/{id}/restore

Restore an archived board within boards.max (owner/admin)

Authentication
API key or Dashboard session; API key scope admin
Operation id
restoreBoard
Idempotency
Send an Idempotency-Key to make retries safe.
Path parameters
NameTypeRequired
idstring (uuid)Yes
Headers
NameTypeRequired
x-workspacestring (uuid)Yes
idempotency-keystringpattern ^[A-Za-z0-9_.:-]{8,128}$No
Response 200: 14 fields
Response 200 (application/json)
NameTypeRequired
idstring (uuid)Yes
workspace_idstring (uuid)Yes
namestringlength 1–100Yes
slugstringlength 3–32pattern ^[a-z0-9][a-z0-9-]*[a-z0-9]$Yes
descriptionstringlength ≤ 2000Yes
visibility"public" | "private" | "unlisted"Yes
require_approvalbooleanYes
anonymous_votingbooleanYes
multi_votebooleanYes
show_on_roadmapbooleanYes
positionintegervalue ≥ 0Yes
archived_atstring (date-time) | nullYes
created_atstring (date-time)Yes
updated_atstring (date-time)Yes

Errors: 400, 401, 403, 404, 409, 413, 422, 429, 500, 503, all in the standard error shape.

curl
curl -X POST 'https://api.upvoiced.com/v1/boards/0190f5e2-4c1d-7a3b-8c2d-5e6f7a8b9c0d/restore' \
  -H "Authorization: Bearer $UPVOICED_API_KEY" \
  -H "X-Workspace: $UPVOICED_WORKSPACE_ID" \
  -H "Idempotency-Key: $(uuidgen)" \
  -H "Content-Type: application/json" \
  -d '{}'
TypeScript SDK
const data = await upvoiced.post('/v1/boards/{id}/restore', {
  path: { id: '0190f5e2-4c1d-7a3b-8c2d-5e6f7a8b9c0d' },
  body: {},
});
MCP

No MCP tool for this operation. The MCP server covers the everyday reads and writes.