diff --git a/src/auto-reply/reply/session-hooks-context.test.ts b/src/auto-reply/reply/session-hooks-context.test.ts index 8d7f66e73e2..9fc2f7a025a 100644 --- a/src/auto-reply/reply/session-hooks-context.test.ts +++ b/src/auto-reply/reply/session-hooks-context.test.ts @@ -135,6 +135,15 @@ async function initStoredSessionState(params: { }); } +function expectFields(value: unknown, expected: Record): void { + expect(value).toBeTypeOf("object"); + expect(value).not.toBeNull(); + const record = value as Record; + for (const [key, expectedValue] of Object.entries(expected)) { + expect(record[key], key).toEqual(expectedValue); + } +} + describe("session hook context wiring", () => { beforeEach(() => { hookRunnerMocks.hasHooks.mockReset(); @@ -168,9 +177,8 @@ describe("session hook context wiring", () => { expect(hookRunnerMocks.runSessionStart).toHaveBeenCalledTimes(1); const [event, context] = hookRunnerMocks.runSessionStart.mock.calls[0] ?? []; - expect(event).toMatchObject({ sessionKey }); - expect(context).toMatchObject({ sessionKey, agentId: "main" }); - expect(context).toMatchObject({ sessionId: event?.sessionId }); + expectFields(event, { sessionKey }); + expectFields(context, { sessionKey, agentId: "main", sessionId: event?.sessionId }); }); it("passes sessionKey to session_end hook context on reset", async () => { @@ -191,19 +199,18 @@ describe("session hook context wiring", () => { expect(hookRunnerMocks.runSessionEnd).toHaveBeenCalledTimes(1); expect(hookRunnerMocks.runSessionStart).toHaveBeenCalledTimes(1); const [event, context] = hookRunnerMocks.runSessionEnd.mock.calls[0] ?? []; - expect(event).toMatchObject({ + expectFields(event, { sessionKey, reason: "new", transcriptArchived: true, }); - expect(context).toMatchObject({ sessionKey, agentId: "main" }); - expect(context).toMatchObject({ sessionId: event?.sessionId }); + expectFields(context, { sessionKey, agentId: "main", sessionId: event?.sessionId }); expect(event?.sessionFile).toContain(".jsonl.reset."); const [startEvent, startContext] = hookRunnerMocks.runSessionStart.mock.calls[0] ?? []; - expect(startEvent).toMatchObject({ resumedFrom: "old-session" }); + expectFields(startEvent, { resumedFrom: "old-session" }); expect(event?.nextSessionId).toBe(startEvent?.sessionId); - expect(startContext).toMatchObject({ sessionId: startEvent?.sessionId }); + expectFields(startContext, { sessionId: startEvent?.sessionId }); }); it("marks explicit /reset rollovers with reason reset", async () => { @@ -223,7 +230,7 @@ describe("session hook context wiring", () => { }); const [event] = hookRunnerMocks.runSessionEnd.mock.calls[0] ?? []; - expect(event).toMatchObject({ reason: "reset" }); + expectFields(event, { reason: "reset" }); }); it("maps custom reset trigger aliases to the new-session reason", async () => { @@ -248,7 +255,7 @@ describe("session hook context wiring", () => { }); const [event] = hookRunnerMocks.runSessionEnd.mock.calls[0] ?? []; - expect(event).toMatchObject({ reason: "new" }); + expectFields(event, { reason: "new" }); }); it("marks daily stale rollovers and exposes the archived transcript path", async () => { @@ -266,7 +273,7 @@ describe("session hook context wiring", () => { const [event] = hookRunnerMocks.runSessionEnd.mock.calls[0] ?? []; const [startEvent] = hookRunnerMocks.runSessionStart.mock.calls[0] ?? []; - expect(event).toMatchObject({ + expectFields(event, { reason: "daily", transcriptArchived: true, }); @@ -295,7 +302,7 @@ describe("session hook context wiring", () => { }); const [event] = hookRunnerMocks.runSessionEnd.mock.calls[0] ?? []; - expect(event).toMatchObject({ reason: "idle" }); + expectFields(event, { reason: "idle" }); } finally { vi.useRealTimers(); } @@ -320,7 +327,7 @@ describe("session hook context wiring", () => { }); const [event] = hookRunnerMocks.runSessionEnd.mock.calls[0] ?? []; - expect(event).toMatchObject({ reason: "idle" }); + expectFields(event, { reason: "idle" }); } finally { vi.useRealTimers(); }