3.5 KiB
Triage Duplicate Detection Post-Mortem (FN-4774)
Summary
Between 14:29 and 16:05 on 2026-05-16, three independent tasks were filed and executed for the same defect: rebase-merge done-task diff truncation in packages/dashboard/src/routes/register-session-diff-routes.ts (with related tests in packages/dashboard/src/__tests__/routes-diff.test.ts). This duplicated implementation and review effort.
Timeline
- FN-4726
- Created: 14:29
- Merged: 14:52
- GitHub tracking: #400
- Scope touched:
register-session-diff-routes.ts,routes-diff.test.ts
- FN-4734
- Created: 14:54
- Finalization: 15:33 (auto no-op finalize)
- GitHub tracking: #414
- Scope touched: same target files
- FN-4741
- Created: 15:04
- Merged: 16:05
- GitHub tracking: #424
- Scope touched: same target files
Root cause
- Triage duplicate scan blind spot:
fn_task_listintentionally excludesdonetasks (tasks.filter((t) => t.column !== "done")inpackages/engine/src/triage.ts), so recently completed fixes were invisible to the duplicate check. - No triage keyword search tool: Triage had no exposed keyword search over full task history (including done/archived), despite
TaskStore.searchTasks(...)already existing and backed by FTS5. - GitHub issue duplication gap: Tracking issue creation did not include a check for existing closed issues covering the same files/keywords.
Decision
- Add
fn_task_searchtriage tool that wrapsstore.searchTasks(...)with defaults that include historical tasks (includeArchived: true, done tasks included by default). - Strengthen duplicate-check prompt guidance so triage must run both list and keyword search (multiple phrases from title/description/file paths/symptoms/symbol names), then inspect likely matches before filing.
- Record GitHub-side dedup as follow-up work (new task) rather than expanding this fix’s scope.
Acceptance-criteria mapping
- Document what happened and why: covered by timeline + root-cause analysis above.
- Close triage duplicate-detection gap: addressed by adding
fn_task_searchand prompt instructions to query done/archived history. - Preserve scope discipline: GitHub-side dedup is explicitly deferred into a follow-up task instead of being implemented here.
Incident closure (FN-4866)
FN-4866 was filed as a follow-up investigation request for the same FN-4726/FN-4734 duplicate-merge incident and is now closed against previously shipped safeguards.
- FN-4774 — Added the
fn_task_searchtriage tool overstore.searchTasks(...)(FTS5) with historical coverage defaults (includeArchived: true, done tasks included by default) and updated duplicate-check prompt guidance inpackages/engine/src/triage.ts. - FN-4815 — Added regression coverage in
packages/engine/src/__tests__/triage-duplicate-search-regression.test.tsfor the tool contract, duplicate-check prompt guidance, and end-to-end duplicate discovery before task creation. - FN-4829 — Added create-time duplicate gating (
POST /tasks/duplicate-check,acknowledgedDuplicates/bypassDuplicateCheckonPOST /tasks,DuplicateWarningModal, andtask:duplicate-warning-overriddenactivity event).
FN-4866 acceptance-criteria mapping: root-cause analysis ✓ (see Root cause above); safeguard recommendation with linked implementation tasks ✓ (FN-4774 and FN-4829); regression test plan ✓ (FN-4815, plus explicit named-case coverage added under this closure task).