Three related fixes, all originating from a `[api:error] Request failed`
log line showing a 500 on `GET /api/tasks/FN-8610/runtime-fallback`.
1. Missing/deleted tasks now return 404 instead of 500.
`getTaskImpl` signalled a miss with a bare `Error`, and route catches
only mapped errno `ENOENT` to 404 — a leftover from the file-backed
storage era. In Postgres mode nothing sets an errno code, so every
unknown/missing/soft-deleted/wrong-project read returned 500. Adds a
typed `TaskNotFoundError` (message byte-identical) plus a shared
`task-lookup-error` mapper applied across the task, session-diff,
git/GitHub, workflow and file-workspace route registrars. The same
bare throw existed on both archive-lifecycle delete paths, so
`DELETE /tasks/:id` was affected too.
2. 5xx logs now carry the origin stack.
`rethrowAsApiError` constructed a fresh `ApiError` from the message
and discarded the original, so the `FNXC:ApiErrorDiagnostics`
contract logged the rethrow site rather than the throw site — the
reported log entry had no stack at all. Threads `cause` through the
error factories and walks the chain (bounded, cycle-guarded).
3. Task deletions are attributable, and non-operator deletes notify.
`task:deleted` audit rows recorded `agentId: "system"` for every HTTP
delete, making an operator click indistinguishable from a script or
an agent; the calling agent's task id was accepted by the store and
then never persisted. Adds a `callerKind` union recorded in audit
metadata, tags every delete call site, and stamps a self-reported
`x-fusion-client` header from the dashboard client. When the caller
is `agent-tool` or `api-unattributed`, a best-effort notice is sent
to the operator mailbox; operator and engine deletes stay silent.
`x-fusion-client` is attribution, not authentication — anything can send
it. No delete-blocking, gating or permission logic is added here.
Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
## Summary
Task cards now remove the overseer eye as soon as their workflow's
effective oversight becomes `off`, instead of reusing an active value
cached before the setting changed.
The invalidation covers card remounts as well as mounted cards, and
authoritative writes from the dashboard, agents, and configuration
rollback reach the board through the existing project-scoped SSE stream.
Older in-flight responses cannot restore the eye after a newer `off`
value wins, while unrelated workflow-setting saves leave active
indicators undisturbed.
## Validation
- 99 focused dashboard regression tests passed across selected and
aggregate cards, desktop and mobile, SSE delivery, and out-of-order
responses
- Core and dashboard typechecks passed
- `pnpm lint` and `pnpm check:changesets` passed
- `pnpm verify:fast` passed production builds and the CLI/server boot
smoke
<!-- This is an auto-generated comment: release notes by coderabbit.ai
-->
## Summary by CodeRabbit
- **Bug Fixes**
- Planner-overseer eye badges now disappear immediately when workflow
oversight is turned off.
- Prevented stale or out-of-order updates from displaying incorrect
oversight status.
- Oversight indicators now remain hidden when the effective setting
cannot be confirmed.
- Live workflow setting changes now update task cards without requiring
a page refresh.
- **Documentation**
- Clarified eye badge visibility rules, tooltip meaning, and active
oversight states in the dashboard guide.
<!-- end of auto-generated comment: release notes by coderabbit.ai -->
## Summary
Follow-up to PR #2086 addressing two Greptile review findings.
## P2 — Missing `psql` binary guard (Greptile P2)
`hasPg` in `_helpers.ts` previously checked only TCP connectivity to
PostgreSQL. But `adminExecAsync()` shells out to the `psql` CLI for DDL
(`CREATE/DROP DATABASE`). On a runner where Postgres is reachable but
`psql` isn't installed, tests would fail with `spawn psql ENOENT`
instead of skipping cleanly.
**Fix**: Added `hasPsql = spawnSync("psql", ["--version"]).status === 0`
to the `hasPg` guard, so tests skip when either Postgres is unreachable
OR `psql` is missing.
## P1 — Expired quarantine entries (Greptile P1)
The 16 dashboard test files quarantined on 2026-06-25 were past the
14-day deletion ratchet (AGENTS.md: "DELETED after 14 days unless
rescued"). Per the ratchet, the test files were deleted and all
references removed:
- **Deleted 16 test files** (CSS drift, mock drift, mobile-render
regressions)
- **Removed 16 entries** from `scripts/lib/test-quarantine.json` (only
the CLI entry remains)
- **Emptied `quarantinedDashboardTests` array** in
`packages/dashboard/vitest.config.ts`
## Verification
| Check | Result |
|---|---|
| Merge gate (`pnpm test:gate`) | ✅ 294 + 99 + 63 = 456 passed |
| Dashboard curated-gate | ✅ passes (891 files, 892 executed, 1
skip-listed, 1 quarantined) |
| Typecheck (engine) | ✅ clean |
| Lint | ✅ exit 0 |
<!-- This is an auto-generated comment: release notes by coderabbit.ai
-->
## Summary by CodeRabbit
* **Tests**
* Removed multiple outdated dashboard UI, CSS/token, theme contrast, and
API/route test suites.
* Updated dashboard test configuration to stop excluding quarantined
tests and to prune the quality shard to the current set.
* Updated the Vitest split/config guard to match the new test fixture
set.
* Improved PostgreSQL test detection by requiring the `psql` CLI before
running database checks.
* Adjusted quarantine tracking by adding a new CLI extension
distribution ledger entry and removing obsolete dashboard quarantine
entries.
<!-- end of auto-generated comment: release notes by coderabbit.ai -->
Make the AI mission planning workspace movable on desktop and safer when streams fail.
- Host the Plan Mission with AI modal in FloatingWindow with desktop drag/resize geometry and mobile full-screen preservation.
- Normalize terminal mission interview stream failures, close SSE/keepalive once, and suppress duplicate late terminal events.
- Cover modal geometry and stream-error behavior with dashboard tests and document the operator-facing behavior.
Files changed:
.changeset/fn-6975-mission-modal-stream.md | 7 ++
docs/dashboard-guide.md | 7 ++
.../api/__tests__/mission-interview-stream.test.ts | 98 ++++++++++++++++++
packages/dashboard/app/api/legacy.ts | 66 ++++++++++---
.../app/components/MissionInterviewModal.css | 51 ++++++++++
.../app/components/MissionInterviewModal.tsx | 37 ++++---
.../__tests__/MissionInterviewModal.test.tsx | 110 ++++++++++++++++++++-
7 files changed, 344 insertions(+), 32 deletions(-)
Fusion-Task-Id: FN-6975
Fusion-Task-Lineage: b2ffa558-8b7e-4a46-8882-f2c4f6189831
Adds a regression test for the PrInfo endpoint to guard against FN-4971, covering the legacy PR info API path in the dashboard package.
Fusion-Task-Id: FN-4971
Fixes chat streaming delta spacing to preserve proper whitespace, adding regression tests for legacy chat stream handlers and the createChatStreamHandlers factory. A changeset was created for the `@runfusion/fusion` package.
Fusion-Task-Id: FN-3817
- Increase the member role text sizing in CreateRoomModal for better readability
- Update CreateRoomModal.css with the adjusted typography value
- Keep the change scoped to create-room role styling only
Fusion-Task-Id: FN-3808
- Add a first-event watchdog in legacy chat SSE handling to prevent hangs before initial stream data
- Cover watchdog behavior with legacy chat stream API tests
- Add hook-level regression tests for useChat and useQuickChat first-send stream scenarios
- Include a changeset for @runfusion/fusion patch release
Fusion-Task-Id: FN-3760
Documentation delivery alignment completing Step 5 of FN-3369, updating the CLI reference, research docs, and research hardening preflight guide with consistent documentation delivery guidance across all three files.
Fusion-Task-Id: FN-3599
This merge splits the monolithic TaskDetailModal test file into six focused test suites (rendering, attachments/tabs, definition/actions, inline-editing/integrations, models/progress/workflow, responsive/dependencies), adds a changeset for the test isolation baseline, fixes chat SSE optimistic echo
Fusion-Task-Id: FN-3609
- Add plugin setup API coverage for migration and sync edge cases
- Expand plugin route tests and implementation safeguards for setup state handling
- Update legacy API glue to align plugin setup responses with route behavior
- Keep test-isolation runtime ignore handling compatible with live app activity
Fusion-Task-Id: FN-3573
This merge adds done-payload snapshot handling across the chat system (FN-3430), normalizing how final assistant messages are preserved and consumed in the dashboard hooks, plus it normalizes dashboard mailbox and user identity for inter-agent messaging (FN-3484) and introduces plugin workflow step
Fusion-Task-Id: FN-3430
Merges a batch of five commits delivering dashboard performance optimizations (new composite indexes on `tasks.column`/`tasks.updatedAt` and debounced detail fetches), hardened chat SSE parsing with new test coverage, restored typecheck gates, split-pane task-link navigation (FN-3191), and research
Fusion-Task-Id: FN-3243