NoteBugsDocs

Referência da API

Epics

O agrupamento de entrega dentro de um projeto.

É a única criação que não pede tenantId: o epic herda o espaço do projeto. Com a feature desligada nas Configurações, todas estas rotas respondem 403.

GET/api/epics
Papel: LeitorEspaço de trabalho

Os epics de todos os espaços que a conta alcança.

Requisição

curl -s http://localhost:3000/api/epics \
  -H "Authorization: Bearer $TOKEN"

Resposta200

[
  {
    "id": "cmttg1vs50015lf010l6k38uq",
    "projectId": "cmttg1vjy000zlf015g097nhi",
    "name": "Onboarding",
    "description": null,
    "color": "amber",
    "status": "ACTIVE",
    "locked": false,
    "dueAt": "2026-10-31T23:59:00.000Z",
    "dueAtZone": "America/Sao_Paulo",
    "position": 0
  }
]

Respostas de erro

CódigoQuando acontece
401Sem credencial, ou com uma que não vale mais. Mande o cookie de sessão ou o cabeçalho Authorization: Bearer.

O epic não tem tenantId (ele herda o do projeto), então o filtro passa pelo projeto.

POST/api/epics
Papel: MembroEspaço de trabalho

Cria um epic dentro de um projeto.

Corpo da requisição

CampoTipoDescrição
projectIdobrigatóriocuidObrigatório: epic solto não existe. O espaço de trabalho vem daqui.
nameobrigatóriostring
descriptionstring | null
coloracento ou #rrggbb
dueAtISO 8601 | nullO alvo do epic. Cards que entram nele podem herdar esta data.
dueAtZoneIANA | null

Requisição

curl -s -X POST http://localhost:3000/api/epics \
  -H "Authorization: Bearer $TOKEN" \
  -H "Content-Type: application/json" \
  -d '{
    "projectId": "cmttg1vjy000zlf015g097nhi",
    "name": "Onboarding",
    "color": "amber",
    "dueAt": "2026-10-31T23:59:00.000Z",
    "dueAtZone": "America/Sao_Paulo"
  }'

Resposta201

{
  "id": "cmttg1vs50015lf010l6k38uq",
  "projectId": "cmttg1vjy000zlf015g097nhi",
  "name": "Onboarding",
  "description": null,
  "color": "amber",
  "status": "ACTIVE",
  "locked": false,
  "dueAt": "2026-10-31T23:59:00.000Z",
  "dueAtZone": "America/Sao_Paulo",
  "position": 0
}

Respostas de erro

CódigoQuando acontece
401Sem credencial, ou com uma que não vale mais. Mande o cookie de sessão ou o cabeçalho Authorization: Bearer.
403Os epics estão desligados nas Configurações desta instalação.
403A conta não alcança o espaço de trabalho do recurso. É 403 e não 404 de propósito: assim a resposta não revela quais espaços existem.
404O recurso não existe, ou já foi apagado.
422O corpo não passou pelo schema. O campo details traz fieldErrors e formErrors do zod, campo a campo.

Esta é a única rota de criação que não pede tenantId.

PATCH/api/epics/[id]
Papel: MembroEspaço de trabalho

Edita o epic: nome, cor, prazo, trava e conclusão.

Parâmetros de rota

CampoTipoDescrição
idobrigatóriocuid

Corpo da requisição

CampoTipoDescrição
namestring
descriptionstring | null
coloracento ou #rrggbb
statusenumDONE conclui o epic, e exige decidir o destino dos cards pendentes.ACTIVE · DONE
lockedbooleanTrava o epic: ele para de receber cards novos. Reversível e sem efeito colateral.
dueAtISO 8601 | null
dueAtZoneIANA | null
pendingCardsenumDONE conclui os cards onde eles estão; MOVE os manda para outro epic.DONE · MOVE
pendingEpicIdcuidO epic de destino, e só quando pendingCards é MOVE.
alignDueAtbooleanSobrescreve a data de quem vence depois do alvo, na movimentação dos pendentes.

Requisição

# trava o epic: ele para de receber cards novos
curl -s -X PATCH http://localhost:3000/api/epics/cmttg1vs50015lf010l6k38uq \
  -H "Authorization: Bearer $TOKEN" \
  -H "Content-Type: application/json" \
  -d '{ "locked": true }'

# conclui, decidindo o destino dos cards que ainda estão pendentes
curl -s -X PATCH http://localhost:3000/api/epics/cmttg1vs50015lf010l6k38uq \
  -H "Authorization: Bearer $TOKEN" \
  -H "Content-Type: application/json" \
  -d '{ "status": "DONE", "pendingCards": "DONE" }'

Resposta200

{
  "id": "cmttg1vs50015lf010l6k38uq",
  "projectId": "cmttg1vjy000zlf015g097nhi",
  "name": "Onboarding",
  "description": null,
  "color": "amber",
  "status": "ACTIVE",
  "locked": true,
  "dueAt": "2026-10-31T23:59:00.000Z",
  "dueAtZone": "America/Sao_Paulo",
  "position": 0
}

Respostas de erro

CódigoQuando acontece
401Sem credencial, ou com uma que não vale mais. Mande o cookie de sessão ou o cabeçalho Authorization: Bearer.
403Os epics estão desligados nas Configurações desta instalação.
404O recurso não existe, ou já foi apagado.
422Concluir o epic exige decidir o destino dos cards que ainda não chegaram na coluna de conclusão: pendingCards com DONE ou MOVE (e, nesse caso, pendingEpicId).
422O corpo veio vazio. Campo ausente significa não mexe, então um PATCH sem nenhum campo não teria efeito nenhum.

Não existe “deixar como está” para os cards pendentes.

DELETE/api/epics/[id]
Papel: MembroEspaço de trabalho

Apaga o epic. Os cards são liberados e continuam no projeto.

Parâmetros de rota

CampoTipoDescrição
idobrigatóriocuid

Requisição

curl -s -X DELETE http://localhost:3000/api/epics/cmttg1vs50015lf010l6k38uq \
  -H "Authorization: Bearer $TOKEN"

Resposta200

{ "deleted": true, "cardsReleased": 3 }

Respostas de erro

CódigoQuando acontece
401Sem credencial, ou com uma que não vale mais. Mande o cookie de sessão ou o cabeçalho Authorization: Bearer.
403Os epics estão desligados nas Configurações desta instalação.
404O recurso não existe, ou já foi apagado.
PATCH/api/epics/order
Papel: MembroEspaço de trabalho

Reordena os epics de UM projeto.

Recebe um subconjunto, como as colunas e os espaços de trabalho.

Corpo da requisição

CampoTipoDescrição
projectIdobrigatóriocuid
epicIdsobrigatóriocuid[]

Requisição

curl -s -X PATCH http://localhost:3000/api/epics/order \
  -H "Authorization: Bearer $TOKEN" \
  -H "Content-Type: application/json" \
  -d '{
    "projectId": "cmttg1vjy000zlf015g097nhi",
    "epicIds": ["cmttg1vs50015lf010l6k38uq"]
  }'

Resposta200

{ "updated": 0 }

Respostas de erro

CódigoQuando acontece
401Sem credencial, ou com uma que não vale mais. Mande o cookie de sessão ou o cabeçalho Authorization: Bearer.
403Os epics estão desligados nas Configurações desta instalação.
404O recurso não existe, ou já foi apagado.
422Os ids informados não pertencem todos ao mesmo conjunto. A rota recebe um subconjunto, mas ele precisa ser de um lugar só.