Files
openclaw/src/plugins/memory-runtime.test.ts
2026-03-28 06:04:50 +00:00

166 lines
5.2 KiB
TypeScript

import { beforeEach, describe, expect, it, vi } from "vitest";
const resolveRuntimePluginRegistryMock = vi.fn();
const applyPluginAutoEnableMock = vi.fn();
const getMemoryRuntimeMock = vi.fn();
vi.mock("../config/plugin-auto-enable.js", () => ({
applyPluginAutoEnable: (...args: unknown[]) => applyPluginAutoEnableMock(...args),
}));
vi.mock("./loader.js", () => ({
resolveRuntimePluginRegistry: (...args: unknown[]) => resolveRuntimePluginRegistryMock(...args),
}));
vi.mock("./memory-state.js", () => ({
getMemoryRuntime: () => getMemoryRuntimeMock(),
}));
let getActiveMemorySearchManager: typeof import("./memory-runtime.js").getActiveMemorySearchManager;
let resolveActiveMemoryBackendConfig: typeof import("./memory-runtime.js").resolveActiveMemoryBackendConfig;
let closeActiveMemorySearchManagers: typeof import("./memory-runtime.js").closeActiveMemorySearchManagers;
function createMemoryAutoEnableFixture() {
const rawConfig = {
plugins: {},
channels: { memory: { enabled: true } },
};
const autoEnabledConfig = {
...rawConfig,
plugins: {
entries: {
memory: { enabled: true },
},
},
};
return { rawConfig, autoEnabledConfig };
}
function createMemoryRuntimeFixture() {
return {
getMemorySearchManager: vi.fn(async () => ({ manager: null, error: "no index" })),
resolveMemoryBackendConfig: vi.fn(() => ({ backend: "builtin" as const })),
};
}
function expectMemoryRuntimeLoaded(autoEnabledConfig: unknown) {
expect(resolveRuntimePluginRegistryMock).toHaveBeenCalledWith({
config: autoEnabledConfig,
});
}
function expectMemoryAutoEnableApplied(rawConfig: unknown, autoEnabledConfig: unknown) {
expect(applyPluginAutoEnableMock).toHaveBeenCalledWith({
config: rawConfig,
env: process.env,
});
expectMemoryRuntimeLoaded(autoEnabledConfig);
}
function setAutoEnabledMemoryRuntime() {
const { rawConfig, autoEnabledConfig } = createMemoryAutoEnableFixture();
const runtime = createMemoryRuntimeFixture();
applyPluginAutoEnableMock.mockReturnValue({ config: autoEnabledConfig, changes: [] });
getMemoryRuntimeMock.mockReturnValueOnce(undefined).mockReturnValue(runtime);
return { rawConfig, autoEnabledConfig, runtime };
}
function expectNoMemoryRuntimeBootstrap() {
expect(applyPluginAutoEnableMock).not.toHaveBeenCalled();
expect(resolveRuntimePluginRegistryMock).not.toHaveBeenCalled();
}
async function expectAutoEnabledMemoryRuntimeCase(params: {
run: (rawConfig: unknown) => Promise<unknown>;
expectedResult: unknown;
}) {
const { rawConfig, autoEnabledConfig } = setAutoEnabledMemoryRuntime();
const result = await params.run(rawConfig);
if (params.expectedResult !== undefined) {
expect(result).toEqual(params.expectedResult);
}
expectMemoryAutoEnableApplied(rawConfig, autoEnabledConfig);
}
async function expectCloseMemoryRuntimeCase(params: {
config: unknown;
setup: () => { closeAllMemorySearchManagers: ReturnType<typeof vi.fn> } | undefined;
}) {
const runtime = params.setup();
await closeActiveMemorySearchManagers(params.config as never);
if (runtime) {
expect(runtime.closeAllMemorySearchManagers).toHaveBeenCalledTimes(1);
}
expectNoMemoryRuntimeBootstrap();
}
describe("memory runtime auto-enable loading", () => {
beforeEach(async () => {
vi.resetModules();
resolveRuntimePluginRegistryMock.mockReset();
applyPluginAutoEnableMock.mockReset();
getMemoryRuntimeMock.mockReset();
applyPluginAutoEnableMock.mockImplementation((params: { config: unknown }) => ({
config: params.config,
changes: [],
}));
({
getActiveMemorySearchManager,
resolveActiveMemoryBackendConfig,
closeActiveMemorySearchManagers,
} = await import("./memory-runtime.js"));
});
it.each([
{
name: "loads memory runtime from the auto-enabled config snapshot",
run: async (rawConfig: unknown) =>
getActiveMemorySearchManager({
cfg: rawConfig as never,
agentId: "main",
}),
expectedResult: undefined,
},
{
name: "reuses the same auto-enabled load path for backend config resolution",
run: async (rawConfig: unknown) =>
resolveActiveMemoryBackendConfig({
cfg: rawConfig as never,
agentId: "main",
}),
expectedResult: { backend: "builtin" },
},
] as const)("$name", async ({ run, expectedResult }) => {
await expectAutoEnabledMemoryRuntimeCase({ run, expectedResult });
});
it.each([
{
name: "does not bootstrap the memory runtime just to close managers",
config: {
plugins: {},
channels: { memory: { enabled: true } },
},
setup: () => {
getMemoryRuntimeMock.mockReturnValue(undefined);
return undefined;
},
},
{
name: "closes an already-registered memory runtime without reloading plugins",
config: {},
setup: () => {
const runtime = {
closeAllMemorySearchManagers: vi.fn(async () => {}),
};
getMemoryRuntimeMock.mockReturnValue(runtime);
return runtime;
},
},
] as const)("$name", async ({ config, setup }) => {
await expectCloseMemoryRuntimeCase({ config, setup });
});
});