test(session-recovery): isolate recovery mocks
This commit is contained in:
@@ -2,24 +2,27 @@ import { existsSync, readFileSync, rmSync } from "node:fs"
|
|||||||
import { randomUUID } from "node:crypto"
|
import { randomUUID } from "node:crypto"
|
||||||
import { tmpdir } from "node:os"
|
import { tmpdir } from "node:os"
|
||||||
import { join } from "node:path"
|
import { join } from "node:path"
|
||||||
import { describe, expect, it, mock } from "bun:test"
|
import { afterAll, describe, expect, it, mock } from "bun:test"
|
||||||
import { detectErrorType } from "./index"
|
import { detectErrorType } from "./index"
|
||||||
|
|
||||||
const TEST_STORAGE_ROOT = join(tmpdir(), `session-recovery-thinking-prepend-${randomUUID()}`)
|
const TEST_STORAGE_ROOT = join(tmpdir(), `session-recovery-thinking-prepend-${randomUUID()}`)
|
||||||
const TEST_PART_STORAGE = join(TEST_STORAGE_ROOT, "part")
|
const TEST_PART_STORAGE = join(TEST_STORAGE_ROOT, "part")
|
||||||
|
|
||||||
mock.module("../../shared", () => ({
|
mock.module("./constants", () => ({
|
||||||
OPENCODE_STORAGE: TEST_STORAGE_ROOT,
|
OPENCODE_STORAGE: TEST_STORAGE_ROOT,
|
||||||
MESSAGE_STORAGE: join(TEST_STORAGE_ROOT, "message"),
|
MESSAGE_STORAGE: join(TEST_STORAGE_ROOT, "message"),
|
||||||
PART_STORAGE: TEST_PART_STORAGE,
|
PART_STORAGE: TEST_PART_STORAGE,
|
||||||
log: () => {},
|
THINKING_TYPES: new Set(["thinking", "redacted_thinking", "reasoning"]),
|
||||||
isSqliteBackend: () => false,
|
META_TYPES: new Set(["step-start", "step-finish"]),
|
||||||
patchPart: async () => true,
|
CONTENT_TYPES: new Set(["text", "tool", "tool_use", "tool_result"]),
|
||||||
normalizeSDKResponse: <TData>(response: { data?: TData }, fallback: TData) => response.data ?? fallback,
|
|
||||||
}))
|
}))
|
||||||
|
|
||||||
const { prependThinkingPart, prependThinkingPartAsync } = await import("./storage/thinking-prepend")
|
const { prependThinkingPart, prependThinkingPartAsync } = await import("./storage/thinking-prepend")
|
||||||
|
|
||||||
|
afterAll(() => {
|
||||||
|
mock.restore()
|
||||||
|
})
|
||||||
|
|
||||||
describe("detectErrorType", () => {
|
describe("detectErrorType", () => {
|
||||||
describe("thinking_block_order errors", () => {
|
describe("thinking_block_order errors", () => {
|
||||||
it("should detect 'first block' error pattern", () => {
|
it("should detect 'first block' error pattern", () => {
|
||||||
@@ -410,7 +413,15 @@ describe("thinking-prepend", () => {
|
|||||||
)
|
)
|
||||||
const sessionID = "ses_thinking_prepend_async"
|
const sessionID = "ses_thinking_prepend_async"
|
||||||
const targetMessageID = "msg_target_async"
|
const targetMessageID = "msg_target_async"
|
||||||
const patchPartMock = mock(async () => true)
|
const patchPartMock = mock(
|
||||||
|
async (
|
||||||
|
_client: unknown,
|
||||||
|
_sessionID: string,
|
||||||
|
_messageID: string,
|
||||||
|
_partID: string,
|
||||||
|
_body: Record<string, unknown>
|
||||||
|
) => true
|
||||||
|
)
|
||||||
const originalPart = {
|
const originalPart = {
|
||||||
id: "prt_prev_async",
|
id: "prt_prev_async",
|
||||||
type: "thinking",
|
type: "thinking",
|
||||||
@@ -467,7 +478,15 @@ describe("thinking-prepend", () => {
|
|||||||
)
|
)
|
||||||
const sessionID = "ses_thinking_prepend_async_missing"
|
const sessionID = "ses_thinking_prepend_async_missing"
|
||||||
const targetMessageID = "msg_target_async_missing"
|
const targetMessageID = "msg_target_async_missing"
|
||||||
const patchPartMock = mock(async () => true)
|
const patchPartMock = mock(
|
||||||
|
async (
|
||||||
|
_client: unknown,
|
||||||
|
_sessionID: string,
|
||||||
|
_messageID: string,
|
||||||
|
_partID: string,
|
||||||
|
_body: Record<string, unknown>
|
||||||
|
) => true
|
||||||
|
)
|
||||||
const client = {
|
const client = {
|
||||||
session: {
|
session: {
|
||||||
messages: async () => ({
|
messages: async () => ({
|
||||||
@@ -511,7 +530,15 @@ describe("thinking-prepend", () => {
|
|||||||
)
|
)
|
||||||
const sessionID = "ses_thinking_prepend_async_out_of_order"
|
const sessionID = "ses_thinking_prepend_async_out_of_order"
|
||||||
const targetMessageID = "msg_target_async_out_of_order"
|
const targetMessageID = "msg_target_async_out_of_order"
|
||||||
const patchPartMock = mock(async () => true)
|
const patchPartMock = mock(
|
||||||
|
async (
|
||||||
|
_client: unknown,
|
||||||
|
_sessionID: string,
|
||||||
|
_messageID: string,
|
||||||
|
_partID: string,
|
||||||
|
_body: Record<string, unknown>
|
||||||
|
) => true
|
||||||
|
)
|
||||||
const originalPart = {
|
const originalPart = {
|
||||||
id: "prt_z_reused",
|
id: "prt_z_reused",
|
||||||
type: "thinking",
|
type: "thinking",
|
||||||
|
|||||||
@@ -1,4 +1,4 @@
|
|||||||
import { afterEach, beforeEach, describe, expect, it, mock } from "bun:test"
|
import { afterAll, afterEach, beforeEach, describe, expect, it, mock } from "bun:test"
|
||||||
|
|
||||||
import { releaseAllPromptAsyncReservationsForTesting } from "../shared/prompt-async-gate"
|
import { releaseAllPromptAsyncReservationsForTesting } from "../shared/prompt-async-gate"
|
||||||
import type { MessageData } from "./types"
|
import type { MessageData } from "./types"
|
||||||
@@ -17,6 +17,10 @@ mock.module("./storage/parts-reader", () => ({
|
|||||||
|
|
||||||
const { recoverToolResultMissing } = await import("./recover-tool-result-missing")
|
const { recoverToolResultMissing } = await import("./recover-tool-result-missing")
|
||||||
|
|
||||||
|
afterAll(() => {
|
||||||
|
mock.restore()
|
||||||
|
})
|
||||||
|
|
||||||
const failedAssistantMsg: MessageData = {
|
const failedAssistantMsg: MessageData = {
|
||||||
info: { id: "msg_failed", role: "assistant" },
|
info: { id: "msg_failed", role: "assistant" },
|
||||||
parts: [],
|
parts: [],
|
||||||
|
|||||||
@@ -1,4 +1,4 @@
|
|||||||
import { afterEach, beforeEach, describe, expect, it, mock } from "bun:test"
|
import { afterAll, afterEach, beforeEach, describe, expect, it, mock } from "bun:test"
|
||||||
|
|
||||||
import { releaseAllPromptAsyncReservationsForTesting } from "../shared/prompt-async-gate"
|
import { releaseAllPromptAsyncReservationsForTesting } from "../shared/prompt-async-gate"
|
||||||
import type { MessageData } from "./types"
|
import type { MessageData } from "./types"
|
||||||
@@ -20,6 +20,10 @@ mock.module("./storage/parts-reader", () => ({
|
|||||||
|
|
||||||
const { recoverUnavailableTool } = await import("./recover-unavailable-tool")
|
const { recoverUnavailableTool } = await import("./recover-unavailable-tool")
|
||||||
|
|
||||||
|
afterAll(() => {
|
||||||
|
mock.restore()
|
||||||
|
})
|
||||||
|
|
||||||
const failedAssistantMsg: MessageData = {
|
const failedAssistantMsg: MessageData = {
|
||||||
info: { id: "msg_failed", role: "assistant", error: 'No such tool: bash' },
|
info: { id: "msg_failed", role: "assistant", error: 'No such tool: bash' },
|
||||||
parts: [],
|
parts: [],
|
||||||
|
|||||||
Reference in New Issue
Block a user