perf(test): speed up qmd manager suite

This commit is contained in:
Peter Steinberger
2026-02-15 01:08:12 +00:00
parent 2ff5c17917
commit 161222f6fe

View File

@@ -92,6 +92,22 @@ describe("QmdMemoryManager", () => {
let cfg: OpenClawConfig;
const agentId = "main";
async function createManager(params?: { mode?: "full" | "status"; cfg?: OpenClawConfig }) {
const cfgToUse = params?.cfg ?? cfg;
const resolved = resolveMemoryBackendConfig({ cfg: cfgToUse, agentId });
const manager = await QmdMemoryManager.create({
cfg: cfgToUse,
agentId,
resolved,
mode: params?.mode ?? "status",
});
expect(manager).toBeTruthy();
if (!manager) {
throw new Error("manager missing");
}
return { manager, resolved };
}
beforeAll(async () => {
fixtureRoot = await fs.mkdtemp(path.join(os.tmpdir(), "qmd-manager-test-fixtures-"));
});
@@ -134,12 +150,7 @@ describe("QmdMemoryManager", () => {
});
it("debounces back-to-back sync calls", async () => {
const resolved = resolveMemoryBackendConfig({ cfg, agentId });
const manager = await QmdMemoryManager.create({ cfg, agentId, resolved });
expect(manager).toBeTruthy();
if (!manager) {
throw new Error("manager missing");
}
const { manager, resolved } = await createManager();
const baselineCalls = spawnMock.mock.calls.length;
@@ -182,8 +193,7 @@ describe("QmdMemoryManager", () => {
return createMockChild();
});
const resolved = resolveMemoryBackendConfig({ cfg, agentId });
const manager = await QmdMemoryManager.create({ cfg, agentId, resolved });
const { manager } = await createManager({ mode: "full" });
expect(releaseUpdate).not.toBeNull();
releaseUpdate?.();
await manager?.close();
@@ -202,9 +212,7 @@ describe("QmdMemoryManager", () => {
},
} as OpenClawConfig;
const resolved = resolveMemoryBackendConfig({ cfg, agentId });
const manager = await QmdMemoryManager.create({ cfg, agentId, resolved, mode: "status" });
expect(manager).toBeTruthy();
const { manager } = await createManager({ mode: "status" });
expect(spawnMock).not.toHaveBeenCalled();
await manager?.close();
});
@@ -240,7 +248,7 @@ describe("QmdMemoryManager", () => {
});
const resolved = resolveMemoryBackendConfig({ cfg, agentId });
const createPromise = QmdMemoryManager.create({ cfg, agentId, resolved });
const createPromise = QmdMemoryManager.create({ cfg, agentId, resolved, mode: "full" });
await updateSpawned.promise;
let created = false;
void createPromise.then(() => {
@@ -278,9 +286,7 @@ describe("QmdMemoryManager", () => {
return createMockChild();
});
const resolved = resolveMemoryBackendConfig({ cfg, agentId });
const manager = await QmdMemoryManager.create({ cfg, agentId, resolved });
expect(manager).toBeTruthy();
const { manager } = await createManager({ mode: "full" });
await manager?.close();
});
@@ -310,7 +316,7 @@ describe("QmdMemoryManager", () => {
});
const resolved = resolveMemoryBackendConfig({ cfg, agentId });
const createPromise = QmdMemoryManager.create({ cfg, agentId, resolved });
const createPromise = QmdMemoryManager.create({ cfg, agentId, resolved, mode: "status" });
await vi.advanceTimersByTimeAsync(0);
const manager = await createPromise;
expect(manager).toBeTruthy();
@@ -346,12 +352,7 @@ describe("QmdMemoryManager", () => {
return createMockChild();
});
const resolved = resolveMemoryBackendConfig({ cfg, agentId });
const manager = await QmdMemoryManager.create({ cfg, agentId, resolved });
expect(manager).toBeTruthy();
if (!manager) {
throw new Error("manager missing");
}
const { manager, resolved } = await createManager();
const maxResults = resolved.qmd?.limits.maxResults;
if (!maxResults) {
throw new Error("qmd maxResults missing");
@@ -403,12 +404,7 @@ describe("QmdMemoryManager", () => {
return createMockChild();
});
const resolved = resolveMemoryBackendConfig({ cfg, agentId });
const manager = await QmdMemoryManager.create({ cfg, agentId, resolved });
expect(manager).toBeTruthy();
if (!manager) {
throw new Error("manager missing");
}
const { manager, resolved } = await createManager();
const maxResults = resolved.qmd?.limits.maxResults;
if (!maxResults) {
throw new Error("qmd maxResults missing");
@@ -465,12 +461,7 @@ describe("QmdMemoryManager", () => {
return createMockChild();
});
const resolved = resolveMemoryBackendConfig({ cfg, agentId });
const manager = await QmdMemoryManager.create({ cfg, agentId, resolved });
expect(manager).toBeTruthy();
if (!manager) {
throw new Error("manager missing");
}
const { manager } = await createManager();
const inFlight = manager.sync({ reason: "interval" });
const forced = manager.sync({ reason: "manual", force: true });
@@ -530,12 +521,7 @@ describe("QmdMemoryManager", () => {
return createMockChild();
});
const resolved = resolveMemoryBackendConfig({ cfg, agentId });
const manager = await QmdMemoryManager.create({ cfg, agentId, resolved });
expect(manager).toBeTruthy();
if (!manager) {
throw new Error("manager missing");
}
const { manager } = await createManager();
const inFlight = manager.sync({ reason: "interval" });
const forcedOne = manager.sync({ reason: "manual", force: true });
@@ -585,12 +571,7 @@ describe("QmdMemoryManager", () => {
return createMockChild();
});
const resolved = resolveMemoryBackendConfig({ cfg, agentId });
const manager = await QmdMemoryManager.create({ cfg, agentId, resolved });
expect(manager).toBeTruthy();
if (!manager) {
throw new Error("manager missing");
}
const { manager, resolved } = await createManager();
await manager.search("test", { sessionKey: "agent:main:slack:dm:u123" });
const searchCall = spawnMock.mock.calls.find((call) => call[1]?.[0] === "search");
@@ -625,12 +606,7 @@ describe("QmdMemoryManager", () => {
},
} as OpenClawConfig;
const resolved = resolveMemoryBackendConfig({ cfg, agentId });
const manager = await QmdMemoryManager.create({ cfg, agentId, resolved });
expect(manager).toBeTruthy();
if (!manager) {
throw new Error("manager missing");
}
const { manager } = await createManager();
const results = await manager.search("test", { sessionKey: "agent:main:slack:dm:u123" });
expect(results).toEqual([]);
@@ -664,7 +640,7 @@ describe("QmdMemoryManager", () => {
});
const resolved = resolveMemoryBackendConfig({ cfg, agentId });
const createPromise = QmdMemoryManager.create({ cfg, agentId, resolved });
const createPromise = QmdMemoryManager.create({ cfg, agentId, resolved, mode: "status" });
await vi.advanceTimersByTimeAsync(0);
const manager = await createPromise;
expect(manager).toBeTruthy();
@@ -694,12 +670,7 @@ describe("QmdMemoryManager", () => {
},
},
} as OpenClawConfig;
const resolved = resolveMemoryBackendConfig({ cfg, agentId });
const manager = await QmdMemoryManager.create({ cfg, agentId, resolved });
expect(manager).toBeTruthy();
if (!manager) {
throw new Error("manager missing");
}
const { manager } = await createManager();
const isAllowed = (key?: string) =>
(manager as unknown as { isScopeAllowed: (key?: string) => boolean }).isScopeAllowed(key);
@@ -728,12 +699,7 @@ describe("QmdMemoryManager", () => {
},
},
} as OpenClawConfig;
const resolved = resolveMemoryBackendConfig({ cfg, agentId });
const manager = await QmdMemoryManager.create({ cfg, agentId, resolved });
expect(manager).toBeTruthy();
if (!manager) {
throw new Error("manager missing");
}
const { manager } = await createManager();
logWarnMock.mockClear();
const beforeCalls = spawnMock.mock.calls.length;
@@ -748,57 +714,8 @@ describe("QmdMemoryManager", () => {
await manager.close();
});
it("symlinks shared qmd models into the agent cache", async () => {
const defaultCacheHome = path.join(tmpRoot, "default-cache");
const sharedModelsDir = path.join(defaultCacheHome, "qmd", "models");
await fs.mkdir(sharedModelsDir, { recursive: true });
const previousXdgCacheHome = process.env.XDG_CACHE_HOME;
process.env.XDG_CACHE_HOME = defaultCacheHome;
const symlinkSpy = vi.spyOn(fs, "symlink");
try {
const resolved = resolveMemoryBackendConfig({ cfg, agentId });
const manager = await QmdMemoryManager.create({ cfg, agentId, resolved });
expect(manager).toBeTruthy();
if (!manager) {
throw new Error("manager missing");
}
const targetModelsDir = path.join(
stateDir,
"agents",
agentId,
"qmd",
"xdg-cache",
"qmd",
"models",
);
const modelsStat = await fs.lstat(targetModelsDir);
expect(modelsStat.isSymbolicLink() || modelsStat.isDirectory()).toBe(true);
expect(
symlinkSpy.mock.calls.some(
(call) => call[0] === sharedModelsDir && call[1] === targetModelsDir,
),
).toBe(true);
await manager.close();
} finally {
symlinkSpy.mockRestore();
if (previousXdgCacheHome === undefined) {
delete process.env.XDG_CACHE_HOME;
} else {
process.env.XDG_CACHE_HOME = previousXdgCacheHome;
}
}
});
it("blocks non-markdown or symlink reads for qmd paths", async () => {
const resolved = resolveMemoryBackendConfig({ cfg, agentId });
const manager = await QmdMemoryManager.create({ cfg, agentId, resolved });
expect(manager).toBeTruthy();
if (!manager) {
throw new Error("manager missing");
}
const { manager } = await createManager();
const textPath = path.join(workspaceDir, "secret.txt");
await fs.writeFile(textPath, "nope", "utf-8");
@@ -822,12 +739,7 @@ describe("QmdMemoryManager", () => {
const text = Array.from({ length: 50 }, (_, index) => `line-${index + 1}`).join("\n");
await fs.writeFile(path.join(workspaceDir, "window.md"), text, "utf-8");
const resolved = resolveMemoryBackendConfig({ cfg, agentId });
const manager = await QmdMemoryManager.create({ cfg, agentId, resolved });
expect(manager).toBeTruthy();
if (!manager) {
throw new Error("manager missing");
}
const { manager } = await createManager();
const result = await manager.readFile({ relPath: "window.md", from: 10, lines: 3 });
expect(result.text).toBe("line-10\nline-11\nline-12");
@@ -861,12 +773,7 @@ describe("QmdMemoryManager", () => {
},
} as OpenClawConfig;
const resolved = resolveMemoryBackendConfig({ cfg, agentId });
const manager = await QmdMemoryManager.create({ cfg, agentId, resolved });
expect(manager).toBeTruthy();
if (!manager) {
throw new Error("manager missing");
}
const { manager } = await createManager();
const reasonCount = writeFileSpy.mock.calls.length;
await manager.sync({ reason: "manual" });
@@ -890,12 +797,7 @@ describe("QmdMemoryManager", () => {
});
it("throws when sqlite index is busy", async () => {
const resolved = resolveMemoryBackendConfig({ cfg, agentId });
const manager = await QmdMemoryManager.create({ cfg, agentId, resolved });
expect(manager).toBeTruthy();
if (!manager) {
throw new Error("manager missing");
}
const { manager } = await createManager();
const inner = manager as unknown as {
db: { prepare: () => { get: () => never }; close: () => void } | null;
resolveDocLocation: (docid?: string) => Promise<unknown>;
@@ -928,12 +830,7 @@ describe("QmdMemoryManager", () => {
return createMockChild();
});
const resolved = resolveMemoryBackendConfig({ cfg, agentId });
const manager = await QmdMemoryManager.create({ cfg, agentId, resolved });
expect(manager).toBeTruthy();
if (!manager) {
throw new Error("manager missing");
}
const { manager } = await createManager();
const inner = manager as unknown as {
db: { prepare: () => { get: () => never }; close: () => void } | null;
};
@@ -969,12 +866,7 @@ describe("QmdMemoryManager", () => {
return createMockChild();
});
const resolved = resolveMemoryBackendConfig({ cfg, agentId });
const manager = await QmdMemoryManager.create({ cfg, agentId, resolved });
expect(manager).toBeTruthy();
if (!manager) {
throw new Error("manager missing");
}
const { manager } = await createManager();
const inner = manager as unknown as {
db: { prepare: (query: string) => { get: (arg: unknown) => unknown }; close: () => void };
@@ -1027,12 +919,7 @@ describe("QmdMemoryManager", () => {
return createMockChild();
});
const resolved = resolveMemoryBackendConfig({ cfg, agentId });
const manager = await QmdMemoryManager.create({ cfg, agentId, resolved });
expect(manager).toBeTruthy();
if (!manager) {
throw new Error("manager missing");
}
const { manager } = await createManager();
await expect(
manager.search("noise", { sessionKey: "agent:main:slack:dm:u123" }),
@@ -1050,12 +937,7 @@ describe("QmdMemoryManager", () => {
return createMockChild();
});
const resolved = resolveMemoryBackendConfig({ cfg, agentId });
const manager = await QmdMemoryManager.create({ cfg, agentId, resolved });
expect(manager).toBeTruthy();
if (!manager) {
throw new Error("manager missing");
}
const { manager } = await createManager();
await expect(
manager.search("missing", { sessionKey: "agent:main:slack:dm:u123" }),
@@ -1073,12 +955,7 @@ describe("QmdMemoryManager", () => {
return createMockChild();
});
const resolved = resolveMemoryBackendConfig({ cfg, agentId });
const manager = await QmdMemoryManager.create({ cfg, agentId, resolved });
expect(manager).toBeTruthy();
if (!manager) {
throw new Error("manager missing");
}
const { manager } = await createManager();
await expect(
manager.search("missing", { sessionKey: "agent:main:slack:dm:u123" }),
@@ -1096,12 +973,7 @@ describe("QmdMemoryManager", () => {
return createMockChild();
});
const resolved = resolveMemoryBackendConfig({ cfg, agentId });
const manager = await QmdMemoryManager.create({ cfg, agentId, resolved });
expect(manager).toBeTruthy();
if (!manager) {
throw new Error("manager missing");
}
const { manager } = await createManager();
await expect(
manager.search("missing", { sessionKey: "agent:main:slack:dm:u123" }),
@@ -1123,12 +995,7 @@ describe("QmdMemoryManager", () => {
return createMockChild();
});
const resolved = resolveMemoryBackendConfig({ cfg, agentId });
const manager = await QmdMemoryManager.create({ cfg, agentId, resolved });
expect(manager).toBeTruthy();
if (!manager) {
throw new Error("manager missing");
}
const { manager } = await createManager();
await expect(
manager.search("missing", { sessionKey: "agent:main:slack:dm:u123" }),
@@ -1163,8 +1030,7 @@ describe("QmdMemoryManager", () => {
});
it("symlinks default model cache into custom XDG_CACHE_HOME on first run", async () => {
const resolved = resolveMemoryBackendConfig({ cfg, agentId });
const manager = await QmdMemoryManager.create({ cfg, agentId, resolved });
const { manager } = await createManager({ mode: "full" });
expect(manager).toBeTruthy();
const stat = await fs.lstat(customModelsDir);
@@ -1176,7 +1042,7 @@ describe("QmdMemoryManager", () => {
const content = await fs.readFile(path.join(customModelsDir, "model.bin"), "utf-8");
expect(content).toBe("fake-model");
await manager!.close();
await manager.close();
});
it("does not overwrite existing models directory", async () => {
@@ -1184,8 +1050,7 @@ describe("QmdMemoryManager", () => {
await fs.mkdir(customModelsDir, { recursive: true });
await fs.writeFile(path.join(customModelsDir, "custom-model.bin"), "custom");
const resolved = resolveMemoryBackendConfig({ cfg, agentId });
const manager = await QmdMemoryManager.create({ cfg, agentId, resolved });
const { manager } = await createManager({ mode: "full" });
expect(manager).toBeTruthy();
// Should still be a real directory, not a symlink.
@@ -1197,15 +1062,14 @@ describe("QmdMemoryManager", () => {
const content = await fs.readFile(path.join(customModelsDir, "custom-model.bin"), "utf-8");
expect(content).toBe("custom");
await manager!.close();
await manager.close();
});
it("skips symlink when no default models exist", async () => {
// Remove the default models dir.
await fs.rm(defaultModelsDir, { recursive: true, force: true });
const resolved = resolveMemoryBackendConfig({ cfg, agentId });
const manager = await QmdMemoryManager.create({ cfg, agentId, resolved });
const { manager } = await createManager({ mode: "full" });
expect(manager).toBeTruthy();
// Custom models dir should not exist (no symlink created).
@@ -1214,7 +1078,7 @@ describe("QmdMemoryManager", () => {
expect.stringContaining("failed to symlink qmd models directory"),
);
await manager!.close();
await manager.close();
});
});
});