fix(tests): stabilize toast manager and continuation tests
This commit is contained in:
parent
2bf11a8ed7
commit
7fe1a653c8
@ -1,17 +1,20 @@
|
|||||||
import { describe, test, expect, beforeEach, mock } from "bun:test"
|
declare const require: (name: string) => any
|
||||||
import { TaskToastManager } from "./manager"
|
const { describe, test, expect, beforeEach, afterEach, mock } = require("bun:test")
|
||||||
import type { ConcurrencyManager } from "../background-agent/concurrency"
|
import type { ConcurrencyManager } from "../background-agent/concurrency"
|
||||||
|
|
||||||
|
type TaskToastManagerClass = typeof import("./manager").TaskToastManager
|
||||||
|
|
||||||
describe("TaskToastManager", () => {
|
describe("TaskToastManager", () => {
|
||||||
|
let TaskToastManager: TaskToastManagerClass
|
||||||
let mockClient: {
|
let mockClient: {
|
||||||
tui: {
|
tui: {
|
||||||
showToast: ReturnType<typeof mock>
|
showToast: ReturnType<typeof mock>
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
let toastManager: TaskToastManager
|
let toastManager: InstanceType<TaskToastManagerClass>
|
||||||
let mockConcurrencyManager: ConcurrencyManager
|
let mockConcurrencyManager: ConcurrencyManager
|
||||||
|
|
||||||
beforeEach(() => {
|
beforeEach(async () => {
|
||||||
mockClient = {
|
mockClient = {
|
||||||
tui: {
|
tui: {
|
||||||
showToast: mock(() => Promise.resolve()),
|
showToast: mock(() => Promise.resolve()),
|
||||||
@ -20,10 +23,18 @@ describe("TaskToastManager", () => {
|
|||||||
mockConcurrencyManager = {
|
mockConcurrencyManager = {
|
||||||
getConcurrencyLimit: mock(() => 5),
|
getConcurrencyLimit: mock(() => 5),
|
||||||
} as unknown as ConcurrencyManager
|
} as unknown as ConcurrencyManager
|
||||||
|
|
||||||
|
const mod = await import("./manager")
|
||||||
|
TaskToastManager = mod.TaskToastManager
|
||||||
|
|
||||||
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
||||||
toastManager = new TaskToastManager(mockClient as any, mockConcurrencyManager)
|
toastManager = new TaskToastManager(mockClient as any, mockConcurrencyManager)
|
||||||
})
|
})
|
||||||
|
|
||||||
|
afterEach(() => {
|
||||||
|
mock.restore()
|
||||||
|
})
|
||||||
|
|
||||||
describe("skills in toast message", () => {
|
describe("skills in toast message", () => {
|
||||||
test("should display skills when provided", () => {
|
test("should display skills when provided", () => {
|
||||||
// given - a task with skills
|
// given - a task with skills
|
||||||
|
|||||||
@ -217,3 +217,7 @@ export function initTaskToastManager(
|
|||||||
instance = new TaskToastManager(client, concurrencyManager)
|
instance = new TaskToastManager(client, concurrencyManager)
|
||||||
return instance
|
return instance
|
||||||
}
|
}
|
||||||
|
|
||||||
|
export function _resetTaskToastManagerForTesting(): void {
|
||||||
|
instance = null
|
||||||
|
}
|
||||||
|
|||||||
@ -1,8 +1,24 @@
|
|||||||
import { describe, test, expect } from "bun:test"
|
declare const require: (name: string) => any
|
||||||
|
const { describe, test, expect, beforeEach, afterEach, spyOn, mock } = require("bun:test")
|
||||||
import { resolveCategoryExecution } from "./category-resolver"
|
import { resolveCategoryExecution } from "./category-resolver"
|
||||||
import type { ExecutorContext } from "./executor-types"
|
import type { ExecutorContext } from "./executor-types"
|
||||||
|
import * as connectedProvidersCache from "../../shared/connected-providers-cache"
|
||||||
|
|
||||||
describe("resolveCategoryExecution", () => {
|
describe("resolveCategoryExecution", () => {
|
||||||
|
let connectedProvidersSpy: ReturnType<typeof spyOn> | undefined
|
||||||
|
let providerModelsSpy: ReturnType<typeof spyOn> | undefined
|
||||||
|
|
||||||
|
beforeEach(() => {
|
||||||
|
mock.restore()
|
||||||
|
connectedProvidersSpy = spyOn(connectedProvidersCache, "readConnectedProvidersCache").mockReturnValue(null)
|
||||||
|
providerModelsSpy = spyOn(connectedProvidersCache, "readProviderModelsCache").mockReturnValue(null)
|
||||||
|
})
|
||||||
|
|
||||||
|
afterEach(() => {
|
||||||
|
connectedProvidersSpy?.mockRestore()
|
||||||
|
providerModelsSpy?.mockRestore()
|
||||||
|
})
|
||||||
|
|
||||||
const createMockExecutorContext = (): ExecutorContext => ({
|
const createMockExecutorContext = (): ExecutorContext => ({
|
||||||
client: {} as any,
|
client: {} as any,
|
||||||
manager: {} as any,
|
manager: {} as any,
|
||||||
|
|||||||
@ -1,9 +1,9 @@
|
|||||||
declare const require: (name: string) => any
|
const { describe, test, expect, beforeEach, afterEach, mock, spyOn } = require("bun:test")
|
||||||
const { describe, test, expect, beforeEach, afterEach, mock } = require("bun:test")
|
|
||||||
|
|
||||||
describe("executeSyncContinuation - toast cleanup error paths", () => {
|
describe("executeSyncContinuation - toast cleanup error paths", () => {
|
||||||
let removeTaskCalls: string[] = []
|
let removeTaskCalls: string[] = []
|
||||||
let addTaskCalls: any[] = []
|
let addTaskCalls: any[] = []
|
||||||
|
let resetToastManager: (() => void) | null = null
|
||||||
|
|
||||||
beforeEach(() => {
|
beforeEach(() => {
|
||||||
//#given - configure fast timing for all tests
|
//#given - configure fast timing for all tests
|
||||||
@ -19,19 +19,21 @@ describe("executeSyncContinuation - toast cleanup error paths", () => {
|
|||||||
removeTaskCalls = []
|
removeTaskCalls = []
|
||||||
addTaskCalls = []
|
addTaskCalls = []
|
||||||
|
|
||||||
//#given - mock task-toast-manager module
|
//#given - initialize real task toast manager (avoid global module mocks)
|
||||||
const mockToastManager = {
|
const { initTaskToastManager, _resetTaskToastManagerForTesting } = require("../../features/task-toast-manager/manager")
|
||||||
addTask: (task: any) => { addTaskCalls.push(task) },
|
_resetTaskToastManagerForTesting()
|
||||||
removeTask: (id: string) => { removeTaskCalls.push(id) },
|
resetToastManager = _resetTaskToastManagerForTesting
|
||||||
}
|
|
||||||
|
|
||||||
const mockGetTaskToastManager = () => mockToastManager
|
const toastManager = initTaskToastManager({
|
||||||
|
tui: { showToast: mock(() => Promise.resolve()) },
|
||||||
|
})
|
||||||
|
|
||||||
mock.module("../../features/task-toast-manager/index.ts", () => ({
|
spyOn(toastManager, "addTask").mockImplementation((task: any) => {
|
||||||
getTaskToastManager: mockGetTaskToastManager,
|
addTaskCalls.push(task)
|
||||||
TaskToastManager: class {},
|
})
|
||||||
initTaskToastManager: () => mockToastManager,
|
spyOn(toastManager, "removeTask").mockImplementation((id: string) => {
|
||||||
}))
|
removeTaskCalls.push(id)
|
||||||
|
})
|
||||||
|
|
||||||
//#given - mock other dependencies
|
//#given - mock other dependencies
|
||||||
mock.module("./sync-session-poller.ts", () => ({
|
mock.module("./sync-session-poller.ts", () => ({
|
||||||
@ -48,7 +50,9 @@ describe("executeSyncContinuation - toast cleanup error paths", () => {
|
|||||||
const { __resetTimingConfig } = require("./timing")
|
const { __resetTimingConfig } = require("./timing")
|
||||||
__resetTimingConfig()
|
__resetTimingConfig()
|
||||||
|
|
||||||
mock.restore()
|
mock.restore()
|
||||||
|
resetToastManager?.()
|
||||||
|
resetToastManager = null
|
||||||
})
|
})
|
||||||
|
|
||||||
test("removes toast when fetchSyncResult throws", async () => {
|
test("removes toast when fetchSyncResult throws", async () => {
|
||||||
@ -294,14 +298,9 @@ describe("executeSyncContinuation - toast cleanup error paths", () => {
|
|||||||
})
|
})
|
||||||
|
|
||||||
test("no crash when toastManager is null", async () => {
|
test("no crash when toastManager is null", async () => {
|
||||||
//#given - mock task-toast-manager module to return null
|
//#given - reset toast manager instance to null
|
||||||
const mockGetTaskToastManager = () => null
|
const { _resetTaskToastManagerForTesting } = require("../../features/task-toast-manager/manager")
|
||||||
|
_resetTaskToastManagerForTesting()
|
||||||
mock.module("../../features/task-toast-manager/index.ts", () => ({
|
|
||||||
getTaskToastManager: mockGetTaskToastManager,
|
|
||||||
TaskToastManager: class {},
|
|
||||||
initTaskToastManager: () => null,
|
|
||||||
}))
|
|
||||||
|
|
||||||
const mockClient = {
|
const mockClient = {
|
||||||
session: {
|
session: {
|
||||||
|
|||||||
@ -1132,27 +1132,50 @@ describe("sisyphus-task", () => {
|
|||||||
launch: async () => mockTask,
|
launch: async () => mockTask,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
let messagesCallCount = 0
|
||||||
|
|
||||||
const mockClient = {
|
const mockClient = {
|
||||||
session: {
|
session: {
|
||||||
prompt: async () => ({ data: {} }),
|
prompt: async () => ({ data: {} }),
|
||||||
promptAsync: async () => ({ data: {} }),
|
promptAsync: async () => ({ data: {} }),
|
||||||
messages: async () => ({
|
messages: async () => {
|
||||||
data: [
|
messagesCallCount++
|
||||||
{
|
const now = Date.now()
|
||||||
info: { id: "msg_001", role: "user", time: { created: Date.now() } },
|
|
||||||
parts: [{ type: "text", text: "Continue the task" }],
|
const beforeContinuation = [
|
||||||
},
|
{
|
||||||
{
|
info: { id: "msg_001", role: "user", time: { created: now } },
|
||||||
info: { id: "msg_002", role: "assistant", time: { created: Date.now() + 1 }, finish: "end_turn" },
|
parts: [{ type: "text", text: "Previous context" }],
|
||||||
parts: [{ type: "text", text: "This is the continued task result" }],
|
},
|
||||||
},
|
{
|
||||||
],
|
info: { id: "msg_002", role: "assistant", time: { created: now + 1 }, finish: "end_turn" },
|
||||||
}),
|
parts: [{ type: "text", text: "Previous result" }],
|
||||||
status: async () => ({ data: { "ses_continue_test": { type: "idle" } } }),
|
},
|
||||||
},
|
]
|
||||||
config: { get: async () => ({ data: { model: SYSTEM_DEFAULT_MODEL } }) },
|
|
||||||
app: {
|
if (messagesCallCount === 1) {
|
||||||
agents: async () => ({ data: [] }),
|
return { data: beforeContinuation }
|
||||||
|
}
|
||||||
|
|
||||||
|
return {
|
||||||
|
data: [
|
||||||
|
...beforeContinuation,
|
||||||
|
{
|
||||||
|
info: { id: "msg_003", role: "user", time: { created: now + 2 } },
|
||||||
|
parts: [{ type: "text", text: "Continue the task" }],
|
||||||
|
},
|
||||||
|
{
|
||||||
|
info: { id: "msg_004", role: "assistant", time: { created: now + 3 }, finish: "end_turn" },
|
||||||
|
parts: [{ type: "text", text: "This is the continued task result" }],
|
||||||
|
},
|
||||||
|
],
|
||||||
|
}
|
||||||
|
},
|
||||||
|
status: async () => ({ data: { "ses_continue_test": { type: "idle" } } }),
|
||||||
|
},
|
||||||
|
config: { get: async () => ({ data: { model: SYSTEM_DEFAULT_MODEL } }) },
|
||||||
|
app: {
|
||||||
|
agents: async () => ({ data: [] }),
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user