mirror of
https://github.com/openclaw/openclaw.git
synced 2026-05-06 19:00:45 +00:00
fix(memory): keep archive transcript visibility safe
Keep reset/deleted session archives searchable while preserving visibility filtering, and keep internal cron-run archives opaque when live ownership metadata is gone.\n\nRefs #56131.\nThanks @buyitsydney.
This commit is contained in:
@@ -11,6 +11,7 @@ const crossAgentStore = {
|
||||
sessionFile: "/tmp/sessions/w1.jsonl",
|
||||
},
|
||||
};
|
||||
let combinedSessionStore: typeof crossAgentStore | Record<string, never> = crossAgentStore;
|
||||
|
||||
vi.mock("openclaw/plugin-sdk/session-transcript-hit", async (importOriginal) => {
|
||||
const actual =
|
||||
@@ -19,7 +20,7 @@ vi.mock("openclaw/plugin-sdk/session-transcript-hit", async (importOriginal) =>
|
||||
...actual,
|
||||
loadCombinedSessionStoreForGateway: vi.fn(() => ({
|
||||
storePath: "(test)",
|
||||
store: crossAgentStore,
|
||||
store: combinedSessionStore,
|
||||
})),
|
||||
};
|
||||
});
|
||||
@@ -27,6 +28,7 @@ vi.mock("openclaw/plugin-sdk/session-transcript-hit", async (importOriginal) =>
|
||||
describe("filterMemorySearchHitsBySessionVisibility", () => {
|
||||
afterEach(() => {
|
||||
vi.mocked(sessionTranscriptHit.loadCombinedSessionStoreForGateway).mockClear();
|
||||
combinedSessionStore = crossAgentStore;
|
||||
});
|
||||
|
||||
it("drops sessions-sourced hits when requester key is missing (fail closed)", async () => {
|
||||
@@ -148,4 +150,57 @@ describe("filterMemorySearchHitsBySessionVisibility", () => {
|
||||
});
|
||||
expect(filtered).toEqual([]);
|
||||
});
|
||||
|
||||
it("keeps same-agent deleted archive hits using owner metadata when the live store entry is gone", async () => {
|
||||
combinedSessionStore = {};
|
||||
const hit: MemorySearchResult = {
|
||||
path: "sessions/main/deleted-stem.jsonl.deleted.2026-02-16T22-27-33.000Z",
|
||||
source: "sessions",
|
||||
score: 1,
|
||||
snippet: "x",
|
||||
startLine: 1,
|
||||
endLine: 2,
|
||||
};
|
||||
const cfg = asOpenClawConfig({
|
||||
tools: {
|
||||
sessions: { visibility: "agent" },
|
||||
},
|
||||
});
|
||||
|
||||
const filtered = await filterMemorySearchHitsBySessionVisibility({
|
||||
cfg,
|
||||
requesterSessionKey: "agent:main:main",
|
||||
sandboxed: false,
|
||||
hits: [hit],
|
||||
});
|
||||
|
||||
expect(filtered).toEqual([hit]);
|
||||
});
|
||||
|
||||
it("still denies cross-agent deleted archive hits resolved from owner metadata when a2a is disabled", async () => {
|
||||
combinedSessionStore = {};
|
||||
const hit: MemorySearchResult = {
|
||||
path: "sessions/peer/deleted-stem.jsonl.deleted.2026-02-16T22-27-33.000Z",
|
||||
source: "sessions",
|
||||
score: 1,
|
||||
snippet: "x",
|
||||
startLine: 1,
|
||||
endLine: 2,
|
||||
};
|
||||
const cfg = asOpenClawConfig({
|
||||
tools: {
|
||||
sessions: { visibility: "all" },
|
||||
agentToAgent: { enabled: false },
|
||||
},
|
||||
});
|
||||
|
||||
const filtered = await filterMemorySearchHitsBySessionVisibility({
|
||||
cfg,
|
||||
requesterSessionKey: "agent:main:main",
|
||||
sandboxed: false,
|
||||
hits: [hit],
|
||||
});
|
||||
|
||||
expect(filtered).toEqual([]);
|
||||
});
|
||||
});
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
import type { OpenClawConfig } from "openclaw/plugin-sdk/memory-core-host-runtime-core";
|
||||
import type { MemorySearchResult } from "openclaw/plugin-sdk/memory-core-host-runtime-files";
|
||||
import {
|
||||
extractTranscriptStemFromSessionsMemoryHit,
|
||||
extractTranscriptIdentityFromSessionsMemoryHit,
|
||||
loadCombinedSessionStoreForGateway,
|
||||
resolveTranscriptStemToSessionKeys,
|
||||
} from "openclaw/plugin-sdk/session-transcript-hit";
|
||||
@@ -42,13 +42,16 @@ export async function filterMemorySearchHitsBySessionVisibility(params: {
|
||||
if (!params.requesterSessionKey || !guard) {
|
||||
continue;
|
||||
}
|
||||
const stem = extractTranscriptStemFromSessionsMemoryHit(hit.path);
|
||||
if (!stem) {
|
||||
const identity = extractTranscriptIdentityFromSessionsMemoryHit(hit.path);
|
||||
if (!identity) {
|
||||
continue;
|
||||
}
|
||||
const keys = resolveTranscriptStemToSessionKeys({
|
||||
store: combinedSessionStore,
|
||||
stem,
|
||||
stem: identity.stem,
|
||||
...(identity.archived && identity.ownerAgentId
|
||||
? { archivedOwnerAgentId: identity.ownerAgentId }
|
||||
: {}),
|
||||
});
|
||||
if (keys.length === 0) {
|
||||
continue;
|
||||
|
||||
Reference in New Issue
Block a user