feat: sprints with burndown and carry-over
Plan sprints with dates and a goal, run one at a time per project, and put tickets in them from the ticket page. The Sprints tab follows the one under way with its progress and a burndown in tickets or points against the ideal line. Closing a sprint sends what was left to the next one or back to the backlog; the board can be filtered by sprint. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
This commit is contained in:
@@ -31,3 +31,9 @@ export * from './issue-checklist-item-added.event';
|
||||
export * from './issue-checklist-item-updated.event';
|
||||
export * from './issue-checklist-item-removed.event';
|
||||
export * from './issue-ranked.event';
|
||||
export * from './sprint-created.event';
|
||||
export * from './sprint-updated.event';
|
||||
export * from './sprint-started.event';
|
||||
export * from './sprint-closed.event';
|
||||
export * from './sprint-deleted.event';
|
||||
export * from './issue-sprint-changed.event';
|
||||
|
||||
@@ -0,0 +1,16 @@
|
||||
import { AutowiredEvent } from '@task-stream/api/shared/domain';
|
||||
import { TrackerEvent } from './tracker.event';
|
||||
|
||||
/** A ticket was moved in or out of a sprint. */
|
||||
@AutowiredEvent
|
||||
export class IssueSprintChangedEvent extends TrackerEvent {
|
||||
constructor(
|
||||
actorId: string,
|
||||
issueId: string,
|
||||
projectId: string,
|
||||
readonly sprintId: string | null,
|
||||
readonly previousSprintId: string | null,
|
||||
) {
|
||||
super(actorId, issueId, projectId);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,19 @@
|
||||
import { AutowiredEvent } from '@task-stream/api/shared/domain';
|
||||
import { TrackerEvent } from './tracker.event';
|
||||
|
||||
/**
|
||||
* A sprint ended. Its unfinished tickets move to `carryOverTo` (null: back
|
||||
* to the backlog); the SprintCarryOverSaga moves them.
|
||||
*/
|
||||
@AutowiredEvent
|
||||
export class SprintClosedEvent extends TrackerEvent {
|
||||
constructor(
|
||||
actorId: string,
|
||||
sprintId: string,
|
||||
projectId: string,
|
||||
readonly carryOverTo: string | null,
|
||||
readonly unfinishedIssues: number,
|
||||
) {
|
||||
super(actorId, sprintId, projectId);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,14 @@
|
||||
import { AutowiredEvent } from '@task-stream/api/shared/domain';
|
||||
import type { SprintProps } from '../sprint/sprint';
|
||||
import { TrackerEvent } from './tracker.event';
|
||||
|
||||
/** A sprint was planned. */
|
||||
@AutowiredEvent
|
||||
export class SprintCreatedEvent extends TrackerEvent {
|
||||
constructor(
|
||||
actorId: string,
|
||||
readonly sprint: SprintProps,
|
||||
) {
|
||||
super(actorId, sprint.id, sprint.projectId);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,10 @@
|
||||
import { AutowiredEvent } from '@task-stream/api/shared/domain';
|
||||
import { TrackerEvent } from './tracker.event';
|
||||
|
||||
/** A sprint was deleted: its tickets go back to the backlog. */
|
||||
@AutowiredEvent
|
||||
export class SprintDeletedEvent extends TrackerEvent {
|
||||
constructor(actorId: string, sprintId: string, projectId: string) {
|
||||
super(actorId, sprintId, projectId);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,10 @@
|
||||
import { AutowiredEvent } from '@task-stream/api/shared/domain';
|
||||
import { TrackerEvent } from './tracker.event';
|
||||
|
||||
/** A sprint got under way. */
|
||||
@AutowiredEvent
|
||||
export class SprintStartedEvent extends TrackerEvent {
|
||||
constructor(actorId: string, sprintId: string, projectId: string) {
|
||||
super(actorId, sprintId, projectId);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,16 @@
|
||||
import { AutowiredEvent } from '@task-stream/api/shared/domain';
|
||||
import type { SprintDetails } from '../sprint/sprint';
|
||||
import { TrackerEvent } from './tracker.event';
|
||||
|
||||
/** A sprint was renamed, re-dated or got another goal (only what changed). */
|
||||
@AutowiredEvent
|
||||
export class SprintUpdatedEvent extends TrackerEvent {
|
||||
constructor(
|
||||
actorId: string,
|
||||
sprintId: string,
|
||||
projectId: string,
|
||||
readonly changes: SprintDetails,
|
||||
) {
|
||||
super(actorId, sprintId, projectId);
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user