feat: comments marked as decisions, on top of the ticket and searchable
Whoever can change the ticket flags a comment as a decision (new event
CommentDecisionMarkedEvent on the comment). The ticket page lists its
decisions above the description, with a link to the comment in the
conversation (`?comment=<id>` scrolls to it and points at it), and the
search palette finds them by their text across my projects.
API: markDecision / PUT-DELETE /api/comments/{id}/decision; Issue.decisions
and GET /api/issues/{issue}/decisions; decisions(projectId?, search) and
GET /api/projects/{project}/decisions, GET /api/me/decisions. MCP:
mark_decision, search_decisions, and get_issue includes them.
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
This commit is contained in:
@@ -45,6 +45,7 @@ import {
|
||||
ChecklistItemBodyDto,
|
||||
AddCommentDto,
|
||||
CreateIssueDto,
|
||||
DecisionsQueryDto,
|
||||
IssueSearchQueryDto,
|
||||
PresenceBodyDto,
|
||||
LinkIssueDto,
|
||||
@@ -61,7 +62,9 @@ import {
|
||||
ActivityDto,
|
||||
BulkResultDto,
|
||||
CommandResultDto,
|
||||
CommentDto,
|
||||
CommentPageDto,
|
||||
DecisionDto,
|
||||
EpicDto,
|
||||
IssueDto,
|
||||
IssuePageDto,
|
||||
@@ -707,6 +710,57 @@ export class IssuesController {
|
||||
);
|
||||
}
|
||||
|
||||
@Get('issues/:issue/decisions')
|
||||
@ApiOptionalPireonAuth()
|
||||
@ISSUE
|
||||
@ApiOperation({
|
||||
summary: 'Comments of the ticket marked as decisions (oldest first)',
|
||||
})
|
||||
@ApiOkResponse({ type: [CommentDto] })
|
||||
@ApiReadErrors()
|
||||
async issueDecisions(
|
||||
@CurrentUser() me: User | undefined,
|
||||
@Param('issue') issue: string,
|
||||
) {
|
||||
return this.comments.decisions(
|
||||
viewerOf(me),
|
||||
await this.refs.issueId(viewerOf(me), issue),
|
||||
);
|
||||
}
|
||||
|
||||
@Get('projects/:project/decisions')
|
||||
@ApiOptionalPireonAuth()
|
||||
@PROJECT
|
||||
@ApiOperation({
|
||||
summary: "Search a project's decisions (most recent first)",
|
||||
})
|
||||
@ApiOkResponse({ type: [DecisionDto] })
|
||||
@ApiReadErrors()
|
||||
async projectDecisions(
|
||||
@CurrentUser() me: User | undefined,
|
||||
@Param('project') project: string,
|
||||
@Query() query: DecisionsQueryDto,
|
||||
) {
|
||||
return this.comments.searchDecisions(viewerOf(me), {
|
||||
projectId: await this.refs.projectId(viewerOf(me), project),
|
||||
search: query.search,
|
||||
limit: query.limit,
|
||||
});
|
||||
}
|
||||
|
||||
@Get('me/decisions')
|
||||
@ApiOperation({
|
||||
summary: 'Search the decisions of all my projects (most recent first)',
|
||||
})
|
||||
@ApiOkResponse({ type: [DecisionDto] })
|
||||
@ApiReadErrors()
|
||||
myDecisions(@CurrentUser() me: User, @Query() query: DecisionsQueryDto) {
|
||||
return this.comments.searchDecisions(me.id, {
|
||||
search: query.search,
|
||||
limit: query.limit,
|
||||
});
|
||||
}
|
||||
|
||||
@Post('issues/:issue/comments')
|
||||
@ISSUE
|
||||
@ApiOperation({
|
||||
|
||||
Reference in New Issue
Block a user