fix(memory): suggest reindex, not --fix, for a missing qmd index (#116958)

`memory status` always appended "Fix: openclaw memory status --fix"
when any audit issue was present, even when none of the issues were
actually repaired by --fix. A missing qmd index file (qmd-index-missing)
is marked fixable: false, so running the suggested --fix left the
issue unresolved. Gate the --fix hint on at least one fixable issue,
and suggest `openclaw memory index --agent <id>` (which builds a fresh
index) when the qmd index file is missing.
This commit is contained in:
chelsealong
2026-08-01 06:14:59 +08:00
committed by GitHub
parent a3220af4aa
commit fc545773cc
2 changed files with 38 additions and 2 deletions
@@ -552,7 +552,15 @@ export async function runMemoryStatus(
lines.push(` ${issue.severity === "error" ? warn(issue.message) : muted(issue.message)}`);
}
if (!opts.fix) {
lines.push(` ${muted(`Fix: openclaw memory status --fix --agent ${agentId}`)}`);
// Only a subset of audit issues are repaired by `--fix`; a missing qmd
// index needs a reindex instead, so each hint is gated on the matching
// issue actually being present.
if (audit.issues.some((issue) => issue.fixable)) {
lines.push(` ${muted(`Fix: openclaw memory status --fix --agent ${agentId}`)}`);
}
if (audit.issues.some((issue) => issue.code === "qmd-index-missing")) {
lines.push(` ${muted(`Fix: openclaw memory index --agent ${agentId}`)}`);
}
}
}
if (dreamingAudit?.issues.length) {
@@ -562,7 +570,7 @@ export async function runMemoryStatus(
for (const issue of dreamingAudit.issues) {
lines.push(` ${issue.severity === "error" ? warn(issue.message) : muted(issue.message)}`);
}
if (!opts.fix) {
if (!opts.fix && dreamingAudit.issues.some((issue) => issue.fixable)) {
lines.push(` ${muted(`Fix: openclaw memory status --fix --agent ${agentId}`)}`);
}
}
+28
View File
@@ -1450,6 +1450,34 @@ describe("memory cli", () => {
});
});
it("suggests reindexing instead of --fix when the qmd index is missing", async () => {
await withTempWorkspace(async (workspaceDir) => {
const close = vi.fn(async () => {});
const missingDbPath = path.join(qmdFixtureRoot, `missing-${qmdCaseId++}.sqlite`);
mockManager({
probeVectorAvailability: vi.fn(async () => true),
status: () =>
makeMemoryStatus({
backend: "qmd",
provider: "qmd",
model: "qmd",
requestedProvider: "qmd",
workspaceDir,
dbPath: missingDbPath,
}),
close,
});
const log = spyRuntimeLogs(defaultRuntime);
await runMemoryCli(["status"]);
expectLogged(log, "QMD index file is missing.");
expectLogged(log, "Fix: openclaw memory index --agent main");
expectNotLogged(log, "Fix: openclaw memory status --fix --agent main");
expect(close).toHaveBeenCalled();
});
});
it("fails index when qmd db file is empty", async () => {
const close = vi.fn(async () => {});
const sync = vi.fn(async () => {});