feat: epics, subtasks and checklists

Tickets can hang from another one of the same project, three levels deep
at most (epic → ticket → subtask). The ticket page lists its subtasks with
their progress, creates new ones and moves the ticket under an epic; a new
Épicas tab shows every epic and how far it has got. Each ticket also gets a
checklist for the small steps that don't deserve a ticket.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
This commit is contained in:
2026-10-08 13:52:43 +02:00
parent 75323115fb
commit d4da33d4e8
84 changed files with 4719 additions and 79 deletions

View File

@@ -2178,6 +2178,16 @@
}
}
},
{
"name": "parent",
"required": false,
"in": "query",
"description": "Only the tickets hanging from this one (id or key)",
"schema": {
"example": "WEB-3",
"type": "string"
}
},
{
"name": "search",
"required": false,
@@ -2365,6 +2375,92 @@
]
}
},
"/api/projects/{project}/epics": {
"get": {
"description": "With the progress of the tickets hanging from each one (done or cancelled, and story points).",
"operationId": "IssuesController_epics",
"parameters": [
{
"name": "project",
"required": true,
"in": "path",
"description": "Project id or key",
"schema": {
"example": "WEB",
"type": "string"
}
}
],
"responses": {
"200": {
"description": "",
"content": {
"application/json": {
"schema": {
"type": "array",
"items": {
"$ref": "#/components/schemas/EpicDto"
}
}
}
}
},
"400": {
"description": "Invalid input",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/ApiErrorDto"
}
}
}
},
"401": {
"description": "Missing or rejected Pireon token",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/ApiErrorDto"
}
}
}
},
"403": {
"description": "Not a member of the project (or not allowed)",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/ApiErrorDto"
}
}
}
},
"404": {
"description": "Not found",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/ApiErrorDto"
}
}
}
}
},
"security": [
{
"pireon-oauth": []
},
{
"pireon": []
},
{}
],
"summary": "Epics: top-level tickets that group others",
"tags": [
"Issues"
]
}
},
"/api/issues/{issue}": {
"get": {
"operationId": "IssuesController_findOne",
@@ -2890,6 +2986,457 @@
]
}
},
"/api/issues/{issue}/parent": {
"put": {
"description": "Same project, three levels at most (epic → ticket → subtask), no loops. null takes it back to the top.",
"operationId": "IssuesController_setParent",
"parameters": [
{
"name": "issue",
"required": true,
"in": "path",
"description": "Ticket id or key",
"schema": {
"example": "WEB-12",
"type": "string"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SetIssueParentDto"
}
}
}
},
"responses": {
"200": {
"description": "",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/CommandResultDto"
}
}
}
},
"400": {
"description": "Invalid input",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/ApiErrorDto"
}
}
}
},
"401": {
"description": "Missing or rejected Pireon token",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/ApiErrorDto"
}
}
}
},
"403": {
"description": "Not a member of the project (or not allowed)",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/ApiErrorDto"
}
}
}
},
"404": {
"description": "Not found",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/ApiErrorDto"
}
}
}
},
"409": {
"description": "Someone changed it at the same time: retry",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/ApiErrorDto"
}
}
}
},
"422": {
"description": "Business rule (e.g. a transition the workflow forbids)",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/ApiErrorDto"
}
}
}
}
},
"security": [
{
"pireon-oauth": []
},
{
"pireon": []
}
],
"summary": "Place the ticket under an epic or another ticket",
"tags": [
"Issues"
]
}
},
"/api/issues/{issue}/checklist": {
"post": {
"operationId": "IssuesController_addChecklistItem",
"parameters": [
{
"name": "issue",
"required": true,
"in": "path",
"description": "Ticket id or key",
"schema": {
"example": "WEB-12",
"type": "string"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/ChecklistItemBodyDto"
}
}
}
},
"responses": {
"201": {
"description": "",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/CommandResultDto"
}
}
}
},
"400": {
"description": "Invalid input",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/ApiErrorDto"
}
}
}
},
"401": {
"description": "Missing or rejected Pireon token",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/ApiErrorDto"
}
}
}
},
"403": {
"description": "Not a member of the project (or not allowed)",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/ApiErrorDto"
}
}
}
},
"404": {
"description": "Not found",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/ApiErrorDto"
}
}
}
},
"409": {
"description": "Someone changed it at the same time: retry",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/ApiErrorDto"
}
}
}
},
"422": {
"description": "Business rule (e.g. a transition the workflow forbids)",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/ApiErrorDto"
}
}
}
}
},
"security": [
{
"pireon-oauth": []
},
{
"pireon": []
}
],
"summary": "Add a step to the ticket's checklist",
"tags": [
"Issues"
]
}
},
"/api/issues/{issue}/checklist/{item}": {
"patch": {
"operationId": "IssuesController_updateChecklistItem",
"parameters": [
{
"name": "issue",
"required": true,
"in": "path",
"description": "Ticket id or key",
"schema": {
"example": "WEB-12",
"type": "string"
}
},
{
"name": "item",
"required": true,
"in": "path",
"schema": {
"format": "uuid",
"type": "string"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/UpdateChecklistItemDto"
}
}
}
},
"responses": {
"200": {
"description": "",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/CommandResultDto"
}
}
}
},
"400": {
"description": "Invalid input",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/ApiErrorDto"
}
}
}
},
"401": {
"description": "Missing or rejected Pireon token",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/ApiErrorDto"
}
}
}
},
"403": {
"description": "Not a member of the project (or not allowed)",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/ApiErrorDto"
}
}
}
},
"404": {
"description": "Not found",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/ApiErrorDto"
}
}
}
},
"409": {
"description": "Someone changed it at the same time: retry",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/ApiErrorDto"
}
}
}
},
"422": {
"description": "Business rule (e.g. a transition the workflow forbids)",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/ApiErrorDto"
}
}
}
}
},
"security": [
{
"pireon-oauth": []
},
{
"pireon": []
}
],
"summary": "Reword, tick or untick a checklist step",
"tags": [
"Issues"
]
},
"delete": {
"operationId": "IssuesController_removeChecklistItem",
"parameters": [
{
"name": "issue",
"required": true,
"in": "path",
"description": "Ticket id or key",
"schema": {
"example": "WEB-12",
"type": "string"
}
},
{
"name": "item",
"required": true,
"in": "path",
"schema": {
"format": "uuid",
"type": "string"
}
}
],
"responses": {
"200": {
"description": "",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/CommandResultDto"
}
}
}
},
"400": {
"description": "Invalid input",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/ApiErrorDto"
}
}
}
},
"401": {
"description": "Missing or rejected Pireon token",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/ApiErrorDto"
}
}
}
},
"403": {
"description": "Not a member of the project (or not allowed)",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/ApiErrorDto"
}
}
}
},
"404": {
"description": "Not found",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/ApiErrorDto"
}
}
}
},
"409": {
"description": "Someone changed it at the same time: retry",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/ApiErrorDto"
}
}
}
},
"422": {
"description": "Business rule (e.g. a transition the workflow forbids)",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/ApiErrorDto"
}
}
}
}
},
"security": [
{
"pireon-oauth": []
},
{
"pireon": []
}
],
"summary": "Remove a checklist step",
"tags": [
"Issues"
]
}
},
"/api/issues/{issue}/links": {
"post": {
"description": "e.g. WEB-3 DEPENDS_ON API-7, WEB-9 TESTS WEB-3. May cross projects.",
@@ -6213,6 +6760,49 @@
"commentId"
]
},
"IssueParentDto": {
"type": "object",
"properties": {
"id": {
"type": "string",
"format": "uuid"
},
"key": {
"type": "string",
"example": "WEB-3"
},
"title": {
"type": "string",
"example": "Pago con tarjeta"
}
},
"required": [
"id",
"key",
"title"
]
},
"ChecklistItemDto": {
"type": "object",
"properties": {
"id": {
"type": "string",
"format": "uuid"
},
"text": {
"type": "string",
"example": "Actualizar el changelog"
},
"done": {
"type": "boolean"
}
},
"required": [
"id",
"text",
"done"
]
},
"IssueDto": {
"type": "object",
"properties": {
@@ -6340,6 +6930,22 @@
"$ref": "#/components/schemas/UserRefDto"
}
},
"parent": {
"nullable": true,
"description": "The epic or ticket this one breaks down",
"type": "object",
"allOf": [
{
"$ref": "#/components/schemas/IssueParentDto"
}
]
},
"checklist": {
"type": "array",
"items": {
"$ref": "#/components/schemas/ChecklistItemDto"
}
},
"commentCount": {
"type": "number"
},
@@ -6379,6 +6985,8 @@
"links",
"attachments",
"watchers",
"parent",
"checklist",
"commentCount",
"createdAt",
"updatedAt",
@@ -6876,6 +7484,12 @@
"type": "string",
"nullable": true,
"format": "uuid"
},
"parent": {
"type": "string",
"nullable": true,
"example": "WEB-3",
"description": "Epic or ticket of the same project the new one breaks down (id or key)"
}
},
"required": [
@@ -6883,6 +7497,51 @@
"title"
]
},
"ChildProgressDto": {
"type": "object",
"properties": {
"total": {
"type": "number"
},
"finished": {
"type": "number",
"description": "Done or cancelled"
},
"percent": {
"type": "number",
"minimum": 0,
"maximum": 100
},
"storyPoints": {
"type": "number"
},
"finishedStoryPoints": {
"type": "number"
}
},
"required": [
"total",
"finished",
"percent",
"storyPoints",
"finishedStoryPoints"
]
},
"EpicDto": {
"type": "object",
"properties": {
"issue": {
"$ref": "#/components/schemas/IssueDto"
},
"progress": {
"$ref": "#/components/schemas/ChildProgressDto"
}
},
"required": [
"issue",
"progress"
]
},
"UpdateIssueDto": {
"type": "object",
"properties": {
@@ -6983,6 +7642,45 @@
"releaseId"
]
},
"SetIssueParentDto": {
"type": "object",
"properties": {
"parent": {
"type": "string",
"nullable": true,
"example": "WEB-3",
"description": "Epic or ticket of the same project (id or key), or null to take it back to the top"
}
},
"required": [
"parent"
]
},
"ChecklistItemBodyDto": {
"type": "object",
"properties": {
"text": {
"type": "string",
"example": "Actualizar el changelog",
"maxLength": 300
}
},
"required": [
"text"
]
},
"UpdateChecklistItemDto": {
"type": "object",
"properties": {
"text": {
"type": "string",
"maxLength": 300
},
"done": {
"type": "boolean"
}
}
},
"LinkIssueDto": {
"type": "object",
"properties": {

View File

@@ -13,6 +13,11 @@ type Activity {
type: String!
}
input AddChecklistItemInput {
issueId: ID!
text: String!
}
type AreaOption {
archived: Boolean!
id: String!
@@ -57,6 +62,23 @@ input ChangeIssueStatusInput {
status: String!
}
"""A step inside a ticket that does not deserve a ticket of its own"""
type ChecklistItem {
done: Boolean!
id: ID!
text: String!
}
"""How far the tickets hanging from one have got"""
type ChildProgress {
"""Done or cancelled"""
finished: Int!
finishedStoryPoints: Int!
percent: Int!
storyPoints: Int!
total: Int!
}
"""
Writes are acknowledged immediately; the read model catches up asynchronously. Wait for a subscription event with version >= this version to see the change.
"""
@@ -121,6 +143,9 @@ input CreateIssueInput {
"""Figma frame for UI changes"""
figmaUrl: String
labels: [String!]
"""Epic or ticket of the same project the new one breaks down"""
parentId: ID
priority: IssuePriority
projectId: ID!
releaseId: ID
@@ -172,6 +197,12 @@ type DurationStats {
p85Days: Float
}
"""A top-level ticket that groups others, with their progress"""
type Epic {
issue: Issue!
progress: ChildProgress!
}
type FlowSeries {
counts: [Int!]!
status: String!
@@ -185,6 +216,7 @@ type Issue {
area: String
assignee: UserRef
attachments: [Attachment!]!
checklist: [ChecklistItem!]!
commentCount: Int!
comments(limit: Int! = 50, offset: Int! = 0): CommentPage!
createdAt: String!
@@ -204,6 +236,9 @@ type Issue {
linkedIssues: [Issue!]!
links: [IssueLink!]!
number: Int!
"""The epic or ticket this one breaks down"""
parent: IssueParent
priority: IssuePriority!
projectId: ID!
projectKey: String!
@@ -237,6 +272,9 @@ input IssueFilterInput {
assigneeId: ID
categories: [StatusCategory!]
labels: [String!]
"""Only the tickets hanging from this one"""
parentId: ID
priorities: [IssuePriority!]
projectId: ID!
releaseId: ID
@@ -269,6 +307,13 @@ type IssuePage {
total: Int!
}
"""The ticket another one hangs from"""
type IssueParent {
id: ID!
key: String!
title: String!
}
enum IssuePriority {
CRITICAL
HIGH
@@ -317,6 +362,8 @@ type Me {
}
type Mutation {
"""Add a step to a ticket's checklist"""
addChecklistItem(input: AddChecklistItemInput!): CommandResult!
addComment(body: String!, issueId: ID!): CommandResult!
"""Add a Pireon user to the project"""
@@ -357,14 +404,23 @@ type Mutation {
Remove a file from a ticket (whoever uploaded it, or an owner/admin). Upload with the REST API.
"""
removeAttachment(attachmentId: ID!, issueId: ID!): CommandResult!
removeChecklistItem(issueId: ID!, itemId: ID!): CommandResult!
removeProjectMember(projectId: ID!, userId: ID!): CommandResult!
"""
Place a ticket under an epic or another ticket of the same project (null: back to the top). Three levels at most: epic → ticket → subtask.
"""
setIssueParent(issueId: ID!, parentId: ID): CommandResult!
"""Put a ticket in a release (null removes it)"""
setIssueRelease(issueId: ID!, releaseId: ID): CommandResult!
unlinkIssues(input: LinkIssuesInput!): CommandResult!
"""Stop following a ticket"""
unwatchIssue(issueId: ID!): CommandResult!
"""Reword, tick or untick a checklist step"""
updateChecklistItem(input: UpdateChecklistItemInput!): CommandResult!
updateIssue(input: UpdateIssueInput!): CommandResult!
updateNotificationSettings(email: Boolean!): NotificationSettings!
updateProject(input: UpdateProjectInput!): CommandResult!
@@ -541,6 +597,11 @@ type Query {
limit: Int! = 50
projectId: ID!
): [Activity!]!
"""
A project's epics: top-level tickets that group others, with the progress of those
"""
epics(projectId: ID!): [Epic!]!
issue(
"""Issue id or key (e.g. "TS-42")"""
idOrKey: String!
@@ -677,6 +738,13 @@ type Throughput {
week: String!
}
input UpdateChecklistItemInput {
done: Boolean
issueId: ID!
itemId: ID!
text: String
}
input UpdateIssueInput {
"""An area id"""
area: String

View File

@@ -363,6 +363,26 @@ export interface paths {
patch?: never;
trace?: never;
};
"/api/projects/{project}/epics": {
parameters: {
query?: never;
header?: never;
path?: never;
cookie?: never;
};
/**
* Epics: top-level tickets that group others
* @description With the progress of the tickets hanging from each one (done or cancelled, and story points).
*/
get: operations["IssuesController_epics"];
put?: never;
post?: never;
delete?: never;
options?: never;
head?: never;
patch?: never;
trace?: never;
};
"/api/issues/{issue}": {
parameters: {
query?: never;
@@ -435,6 +455,61 @@ export interface paths {
patch?: never;
trace?: never;
};
"/api/issues/{issue}/parent": {
parameters: {
query?: never;
header?: never;
path?: never;
cookie?: never;
};
get?: never;
/**
* Place the ticket under an epic or another ticket
* @description Same project, three levels at most (epic → ticket → subtask), no loops. null takes it back to the top.
*/
put: operations["IssuesController_setParent"];
post?: never;
delete?: never;
options?: never;
head?: never;
patch?: never;
trace?: never;
};
"/api/issues/{issue}/checklist": {
parameters: {
query?: never;
header?: never;
path?: never;
cookie?: never;
};
get?: never;
put?: never;
/** Add a step to the ticket's checklist */
post: operations["IssuesController_addChecklistItem"];
delete?: never;
options?: never;
head?: never;
patch?: never;
trace?: never;
};
"/api/issues/{issue}/checklist/{item}": {
parameters: {
query?: never;
header?: never;
path?: never;
cookie?: never;
};
get?: never;
put?: never;
post?: never;
/** Remove a checklist step */
delete: operations["IssuesController_removeChecklistItem"];
options?: never;
head?: never;
/** Reword, tick or untick a checklist step */
patch: operations["IssuesController_updateChecklistItem"];
trace?: never;
};
"/api/issues/{issue}/links": {
parameters: {
query?: never;
@@ -1071,6 +1146,21 @@ export interface components {
*/
commentId: string | null;
};
IssueParentDto: {
/** Format: uuid */
id: string;
/** @example WEB-3 */
key: string;
/** @example Pago con tarjeta */
title: string;
};
ChecklistItemDto: {
/** Format: uuid */
id: string;
/** @example Actualizar el changelog */
text: string;
done: boolean;
};
IssueDto: {
/** Format: uuid */
id: string;
@@ -1116,6 +1206,9 @@ export interface components {
attachments: components["schemas"]["AttachmentDto"][];
/** @description People following it */
watchers: components["schemas"]["UserRefDto"][];
/** @description The epic or ticket this one breaks down */
parent: components["schemas"]["IssueParentDto"] | null;
checklist: components["schemas"]["ChecklistItemDto"][];
commentCount: number;
/** Format: date-time */
createdAt: string;
@@ -1266,6 +1359,23 @@ export interface components {
assigneeId?: string | null;
/** Format: uuid */
releaseId?: string | null;
/**
* @description Epic or ticket of the same project the new one breaks down (id or key)
* @example WEB-3
*/
parent?: string | null;
};
ChildProgressDto: {
total: number;
/** @description Done or cancelled */
finished: number;
percent: number;
storyPoints: number;
finishedStoryPoints: number;
};
EpicDto: {
issue: components["schemas"]["IssueDto"];
progress: components["schemas"]["ChildProgressDto"];
};
UpdateIssueDto: {
description?: string | null;
@@ -1308,6 +1418,21 @@ export interface components {
*/
releaseId: string | null;
};
SetIssueParentDto: {
/**
* @description Epic or ticket of the same project (id or key), or null to take it back to the top
* @example WEB-3
*/
parent: string | null;
};
ChecklistItemBodyDto: {
/** @example Actualizar el changelog */
text: string;
};
UpdateChecklistItemDto: {
text?: string;
done?: boolean;
};
LinkIssueDto: {
type: components["schemas"]["IssueLinkType"];
/**
@@ -2890,6 +3015,8 @@ export interface operations {
unassigned?: boolean;
releaseId?: string;
label?: string[];
/** @description Only the tickets hanging from this one (id or key) */
parent?: string;
/** @description Matches key, title or description */
search?: string;
};
@@ -3028,6 +3155,64 @@ export interface operations {
};
};
};
IssuesController_epics: {
parameters: {
query?: never;
header?: never;
path: {
/** @description Project id or key */
project: string;
};
cookie?: never;
};
requestBody?: never;
responses: {
200: {
headers: {
[name: string]: unknown;
};
content: {
"application/json": components["schemas"]["EpicDto"][];
};
};
/** @description Invalid input */
400: {
headers: {
[name: string]: unknown;
};
content: {
"application/json": components["schemas"]["ApiErrorDto"];
};
};
/** @description Missing or rejected Pireon token */
401: {
headers: {
[name: string]: unknown;
};
content: {
"application/json": components["schemas"]["ApiErrorDto"];
};
};
/** @description Not a member of the project (or not allowed) */
403: {
headers: {
[name: string]: unknown;
};
content: {
"application/json": components["schemas"]["ApiErrorDto"];
};
};
/** @description Not found */
404: {
headers: {
[name: string]: unknown;
};
content: {
"application/json": components["schemas"]["ApiErrorDto"];
};
};
};
};
IssuesController_findOne: {
parameters: {
query?: never;
@@ -3406,6 +3591,324 @@ export interface operations {
};
};
};
IssuesController_setParent: {
parameters: {
query?: never;
header?: never;
path: {
/** @description Ticket id or key */
issue: string;
};
cookie?: never;
};
requestBody: {
content: {
"application/json": components["schemas"]["SetIssueParentDto"];
};
};
responses: {
200: {
headers: {
[name: string]: unknown;
};
content: {
"application/json": components["schemas"]["CommandResultDto"];
};
};
/** @description Invalid input */
400: {
headers: {
[name: string]: unknown;
};
content: {
"application/json": components["schemas"]["ApiErrorDto"];
};
};
/** @description Missing or rejected Pireon token */
401: {
headers: {
[name: string]: unknown;
};
content: {
"application/json": components["schemas"]["ApiErrorDto"];
};
};
/** @description Not a member of the project (or not allowed) */
403: {
headers: {
[name: string]: unknown;
};
content: {
"application/json": components["schemas"]["ApiErrorDto"];
};
};
/** @description Not found */
404: {
headers: {
[name: string]: unknown;
};
content: {
"application/json": components["schemas"]["ApiErrorDto"];
};
};
/** @description Someone changed it at the same time: retry */
409: {
headers: {
[name: string]: unknown;
};
content: {
"application/json": components["schemas"]["ApiErrorDto"];
};
};
/** @description Business rule (e.g. a transition the workflow forbids) */
422: {
headers: {
[name: string]: unknown;
};
content: {
"application/json": components["schemas"]["ApiErrorDto"];
};
};
};
};
IssuesController_addChecklistItem: {
parameters: {
query?: never;
header?: never;
path: {
/** @description Ticket id or key */
issue: string;
};
cookie?: never;
};
requestBody: {
content: {
"application/json": components["schemas"]["ChecklistItemBodyDto"];
};
};
responses: {
201: {
headers: {
[name: string]: unknown;
};
content: {
"application/json": components["schemas"]["CommandResultDto"];
};
};
/** @description Invalid input */
400: {
headers: {
[name: string]: unknown;
};
content: {
"application/json": components["schemas"]["ApiErrorDto"];
};
};
/** @description Missing or rejected Pireon token */
401: {
headers: {
[name: string]: unknown;
};
content: {
"application/json": components["schemas"]["ApiErrorDto"];
};
};
/** @description Not a member of the project (or not allowed) */
403: {
headers: {
[name: string]: unknown;
};
content: {
"application/json": components["schemas"]["ApiErrorDto"];
};
};
/** @description Not found */
404: {
headers: {
[name: string]: unknown;
};
content: {
"application/json": components["schemas"]["ApiErrorDto"];
};
};
/** @description Someone changed it at the same time: retry */
409: {
headers: {
[name: string]: unknown;
};
content: {
"application/json": components["schemas"]["ApiErrorDto"];
};
};
/** @description Business rule (e.g. a transition the workflow forbids) */
422: {
headers: {
[name: string]: unknown;
};
content: {
"application/json": components["schemas"]["ApiErrorDto"];
};
};
};
};
IssuesController_removeChecklistItem: {
parameters: {
query?: never;
header?: never;
path: {
/** @description Ticket id or key */
issue: string;
item: string;
};
cookie?: never;
};
requestBody?: never;
responses: {
200: {
headers: {
[name: string]: unknown;
};
content: {
"application/json": components["schemas"]["CommandResultDto"];
};
};
/** @description Invalid input */
400: {
headers: {
[name: string]: unknown;
};
content: {
"application/json": components["schemas"]["ApiErrorDto"];
};
};
/** @description Missing or rejected Pireon token */
401: {
headers: {
[name: string]: unknown;
};
content: {
"application/json": components["schemas"]["ApiErrorDto"];
};
};
/** @description Not a member of the project (or not allowed) */
403: {
headers: {
[name: string]: unknown;
};
content: {
"application/json": components["schemas"]["ApiErrorDto"];
};
};
/** @description Not found */
404: {
headers: {
[name: string]: unknown;
};
content: {
"application/json": components["schemas"]["ApiErrorDto"];
};
};
/** @description Someone changed it at the same time: retry */
409: {
headers: {
[name: string]: unknown;
};
content: {
"application/json": components["schemas"]["ApiErrorDto"];
};
};
/** @description Business rule (e.g. a transition the workflow forbids) */
422: {
headers: {
[name: string]: unknown;
};
content: {
"application/json": components["schemas"]["ApiErrorDto"];
};
};
};
};
IssuesController_updateChecklistItem: {
parameters: {
query?: never;
header?: never;
path: {
/** @description Ticket id or key */
issue: string;
item: string;
};
cookie?: never;
};
requestBody: {
content: {
"application/json": components["schemas"]["UpdateChecklistItemDto"];
};
};
responses: {
200: {
headers: {
[name: string]: unknown;
};
content: {
"application/json": components["schemas"]["CommandResultDto"];
};
};
/** @description Invalid input */
400: {
headers: {
[name: string]: unknown;
};
content: {
"application/json": components["schemas"]["ApiErrorDto"];
};
};
/** @description Missing or rejected Pireon token */
401: {
headers: {
[name: string]: unknown;
};
content: {
"application/json": components["schemas"]["ApiErrorDto"];
};
};
/** @description Not a member of the project (or not allowed) */
403: {
headers: {
[name: string]: unknown;
};
content: {
"application/json": components["schemas"]["ApiErrorDto"];
};
};
/** @description Not found */
404: {
headers: {
[name: string]: unknown;
};
content: {
"application/json": components["schemas"]["ApiErrorDto"];
};
};
/** @description Someone changed it at the same time: retry */
409: {
headers: {
[name: string]: unknown;
};
content: {
"application/json": components["schemas"]["ApiErrorDto"];
};
};
/** @description Business rule (e.g. a transition the workflow forbids) */
422: {
headers: {
[name: string]: unknown;
};
content: {
"application/json": components["schemas"]["ApiErrorDto"];
};
};
};
};
IssuesController_link: {
parameters: {
query?: never;

View File

@@ -28,6 +28,7 @@ describe('appRoutes', () => {
'',
'board',
'issues/:issueKey',
'epics',
'releases',
'dashboard',
'analytics',