diff --git a/doc/plans/2026-10-24-recurring-server-sleep-stack.md b/doc/plans/2026-10-24-recurring-server-sleep-stack.md index c9c2984936a..e821d6bb3be 100644 --- a/doc/plans/2026-10-24-recurring-server-sleep-stack.md +++ b/doc/plans/2026-10-24-recurring-server-sleep-stack.md @@ -2074,3 +2074,13 @@ reconciliation, and every other original inventory duty remain outstanding. Final combined owner acceptance passed all 164 tests in five suites, with no skips, in 41.14 seconds using separate dispatch and recovery databases. Together with the 30 retry-route tests this covers 194 tests. Remote PR gates remain pending. + + +## Startup CI fixture repair + +Initial head bd490ee50b failed server shard 4/12: eleven tests in the startup +suite used a heartbeat test double without the new registration method. The +real worker and owner acceptance passed, but startup wiring coverage was missing +from the local selection. The double now exposes the method, and new assertions +verify scheduler enablement and periodic-reaper exclusion. All 48 startup tests +pass in 5.34 seconds. This is a test-only repair; fresh head CI/review is required. diff --git a/doc/plans/2026-10-25-scheduled-retry-cancellation-sleep-audit.md b/doc/plans/2026-10-25-scheduled-retry-cancellation-sleep-audit.md index 424d715b216..a196143bd1f 100644 --- a/doc/plans/2026-10-25-scheduled-retry-cancellation-sleep-audit.md +++ b/doc/plans/2026-10-25-scheduled-retry-cancellation-sleep-audit.md @@ -131,3 +131,13 @@ unfinished. This slice and its parent stack are not authorized for merge. Final combined owner acceptance passed all 164 tests in five suites, with no skips, in 41.14 seconds using separate dispatch and recovery databases. Together with the 30 retry-route tests this covers 194 tests. Remote PR gates remain pending. + + +## Startup CI fixture repair + +Initial head bd490ee50b failed server shard 4/12: eleven tests in the startup +suite used a heartbeat test double without the new registration method. The +real worker and owner acceptance passed, but startup wiring coverage was missing +from the local selection. The double now exposes the method, and new assertions +verify scheduler enablement and periodic-reaper exclusion. All 48 startup tests +pass in 5.34 seconds. This is a test-only repair; fresh head CI/review is required. diff --git a/server/src/__tests__/server-startup-feedback-export.test.ts b/server/src/__tests__/server-startup-feedback-export.test.ts index 4f632aa71ae..377a633ca99 100644 --- a/server/src/__tests__/server-startup-feedback-export.test.ts +++ b/server/src/__tests__/server-startup-feedback-export.test.ts @@ -106,6 +106,7 @@ const { })), reconcileHotRestartAdoption: vi.fn(async () => ({ mode: "none" })), reapOrphanedRuns: vi.fn(async () => ({ reaped: 0, runIds: [] })), + registerScheduledRetryCancellationWork: vi.fn((_coordinator: unknown, _canRun: () => boolean) => ({ ready: Promise.resolve() })), promoteDueScheduledRetries: vi.fn(async () => ({ promoted: 0, runIds: [] })), resumeQueuedRuns: vi.fn(async () => undefined), recoverPendingSessionGoalActions: vi.fn(async () => ({ scanned: 0, enqueued: 0, alreadyQueued: 0, invalid: 0 })), @@ -538,6 +539,18 @@ describe("startServer feedback export wiring", () => { process.env.BETTER_AUTH_SECRET = "test-secret"; }); + it.each([false, true])("registers retry cancellation recovery only when maintenance is enabled (%s)", async enabled => { + loadConfigMock.mockReturnValue(buildTestConfig({ heartbeatSchedulerEnabled: enabled })); + await startServer(); await settleStartupHousekeeping(); + expect(heartbeatServiceMock.registerScheduledRetryCancellationWork).toHaveBeenCalledTimes(enabled ? 1 : 0); + if (enabled) { + const [coordinator, admitted] = heartbeatServiceMock.registerScheduledRetryCancellationWork.mock.calls[0]; + const app = await createAppMock.mock.results.at(-1)!.value; + expect(coordinator).toBe(app.locals.deliveryWork); + expect(admitted()).toBe(true); + } + }); + it.each([false, true])("registers approval queue seeding only when maintenance is enabled (%s)", async enabled => { loadConfigMock.mockReturnValue(buildTestConfig({ heartbeatSchedulerEnabled: enabled })); await startServer(); await settleStartupHousekeeping(); @@ -883,6 +896,7 @@ describe("startServer feedback export wiring", () => { intervalCallback?.(); await new Promise((resolve) => setImmediate(resolve)); expect(heartbeatServiceMock.sweepStaleIssueLocks).toHaveBeenCalledTimes(2); + expect(heartbeatServiceMock.reapOrphanedRuns).toHaveBeenLastCalledWith({ staleThresholdMs: 300_000, skipScheduledRetryCancellation: true }); expect(heartbeatServiceMock.reconcileCostAccounting).toHaveBeenCalledTimes(1); expect(retiredDetector).not.toHaveBeenCalled(); } finally {