import { afterEach, describe, expect, it, vi } from "vitest"; vi.mock("@/lib/rpa/worker-health", () => ({ isAnyRpaWorkerHealthy: vi.fn(), })); vi.mock("@/lib/rpa/spawn-address-candidates", () => ({ spawnFetchMothershipAddressCandidates: vi.fn(), })); vi.mock("@/workers/rpa/queue", () => ({ addAddressCandidatesJob: vi.fn(), })); const redisGet = vi.fn(); vi.mock("@/lib/redis", () => ({ ensureRedisReady: vi.fn().mockResolvedValue(undefined), getRedis: vi.fn(() => ({ setex: vi.fn().mockResolvedValue("OK"), get: redisGet, })), resetRedisClient: vi.fn(), })); import { spawnFetchMothershipAddressCandidates } from "@/lib/rpa/spawn-address-candidates"; import { isAnyRpaWorkerHealthy } from "@/lib/rpa/worker-health"; import { requestMothershipCandidatesViaWorker } from "@/modules/address/candidates-queue"; import { addAddressCandidatesJob } from "@/workers/rpa/queue"; const input = { pickup: { street: "1234 Warehouse Blvd", city: "Los Angeles", state: "CA", zip: "90001", }, delivery: { street: "5678 Distribution Dr", city: "Dallas", state: "TX", zip: "75201", }, }; const mockResult = { pickup_candidates: [{ display_label: "A", option_id: "1" }], delivery_candidates: [{ display_label: "B", option_id: "2" }], requires_selection: false, }; describe("requestMothershipCandidatesViaWorker", () => { afterEach(() => { vi.clearAllMocks(); redisGet.mockReset(); delete process.env.RPA_QUEUE_ENABLED; }); it("Worker 无心跳时默认走 spawn", async () => { delete process.env.RPA_PARKED_SESSION; vi.mocked(isAnyRpaWorkerHealthy).mockResolvedValue(false); vi.mocked(spawnFetchMothershipAddressCandidates).mockResolvedValue( mockResult, ); const result = await requestMothershipCandidatesViaWorker(input); expect(result).toEqual(mockResult); expect(spawnFetchMothershipAddressCandidates).toHaveBeenCalledWith(input); }); it("Worker 无心跳且 RPA_PARKED_SESSION=true 时抛错", async () => { process.env.RPA_QUEUE_ENABLED = "true"; process.env.RPA_PARKED_SESSION = "true"; vi.mocked(isAnyRpaWorkerHealthy).mockResolvedValue(false); await expect(requestMothershipCandidatesViaWorker(input)).rejects.toMatchObject( { code: "PAGE_LOAD_TIMEOUT" }, ); expect(spawnFetchMothershipAddressCandidates).not.toHaveBeenCalled(); }); it("Worker 有心跳时只走队列等待结果,不 spawn", async () => { process.env.RPA_QUEUE_ENABLED = "true"; vi.mocked(isAnyRpaWorkerHealthy).mockResolvedValue(true); vi.mocked(addAddressCandidatesJob).mockResolvedValue(undefined); redisGet .mockResolvedValueOnce(null) .mockResolvedValueOnce( JSON.stringify({ ok: true, data: mockResult }), ); const result = await requestMothershipCandidatesViaWorker(input); expect(result).toEqual(mockResult); expect(addAddressCandidatesJob).toHaveBeenCalled(); expect(spawnFetchMothershipAddressCandidates).not.toHaveBeenCalled(); }); });