mirror of
https://github.com/openclaw/openclaw.git
synced 2026-04-14 02:31:24 +00:00
fix: preserve account binding metadata on rebind
This commit is contained in:
60
extensions/bluebubbles/src/conversation-bindings.test.ts
Normal file
60
extensions/bluebubbles/src/conversation-bindings.test.ts
Normal file
@@ -0,0 +1,60 @@
|
||||
import type { OpenClawConfig } from "openclaw/plugin-sdk/config-runtime";
|
||||
import { getSessionBindingService } from "openclaw/plugin-sdk/conversation-runtime";
|
||||
import { beforeEach, describe, expect, it } from "vitest";
|
||||
import { __testing, createBlueBubblesConversationBindingManager } from "./conversation-bindings.js";
|
||||
|
||||
const baseCfg = {
|
||||
session: { mainKey: "main", scope: "per-sender" },
|
||||
} satisfies OpenClawConfig;
|
||||
|
||||
describe("BlueBubbles conversation bindings", () => {
|
||||
beforeEach(() => {
|
||||
__testing.resetBlueBubblesConversationBindingsForTests();
|
||||
});
|
||||
|
||||
it("preserves existing metadata when rebinding the same conversation", async () => {
|
||||
const manager = createBlueBubblesConversationBindingManager({
|
||||
cfg: baseCfg,
|
||||
accountId: "default",
|
||||
});
|
||||
|
||||
manager.bindConversation({
|
||||
conversationId: "chat-guid-1",
|
||||
targetKind: "subagent",
|
||||
targetSessionKey: "agent:main:subagent:child",
|
||||
metadata: {
|
||||
agentId: "codex",
|
||||
label: "child",
|
||||
boundBy: "system",
|
||||
},
|
||||
});
|
||||
|
||||
await getSessionBindingService().bind({
|
||||
targetSessionKey: "agent:main:subagent:child",
|
||||
targetKind: "subagent",
|
||||
conversation: {
|
||||
channel: "bluebubbles",
|
||||
accountId: "default",
|
||||
conversationId: "chat-guid-1",
|
||||
},
|
||||
placement: "current",
|
||||
metadata: {
|
||||
label: "child",
|
||||
},
|
||||
});
|
||||
|
||||
expect(
|
||||
getSessionBindingService().resolveByConversation({
|
||||
channel: "bluebubbles",
|
||||
accountId: "default",
|
||||
conversationId: "chat-guid-1",
|
||||
}),
|
||||
).toMatchObject({
|
||||
metadata: expect.objectContaining({
|
||||
agentId: "codex",
|
||||
label: "child",
|
||||
boundBy: "system",
|
||||
}),
|
||||
});
|
||||
});
|
||||
});
|
||||
@@ -158,6 +158,9 @@ export function createAccountScopedConversationBindingManager<TKind extends stri
|
||||
if (!normalizedConversationId || !normalizedTargetSessionKey) {
|
||||
return null;
|
||||
}
|
||||
const existing = getState<TKind>(params.stateKey).bindingsByAccountConversation.get(
|
||||
resolveBindingKey({ accountId, conversationId: normalizedConversationId }),
|
||||
);
|
||||
const now = Date.now();
|
||||
const record: AccountScopedConversationBindingRecord<TKind> = {
|
||||
accountId,
|
||||
@@ -167,15 +170,15 @@ export function createAccountScopedConversationBindingManager<TKind extends stri
|
||||
agentId:
|
||||
typeof metadata?.agentId === "string" && metadata.agentId.trim()
|
||||
? metadata.agentId.trim()
|
||||
: resolveAgentIdFromSessionKey(normalizedTargetSessionKey),
|
||||
: (existing?.agentId ?? resolveAgentIdFromSessionKey(normalizedTargetSessionKey)),
|
||||
label:
|
||||
typeof metadata?.label === "string" && metadata.label.trim()
|
||||
? metadata.label.trim()
|
||||
: undefined,
|
||||
: existing?.label,
|
||||
boundBy:
|
||||
typeof metadata?.boundBy === "string" && metadata.boundBy.trim()
|
||||
? metadata.boundBy.trim()
|
||||
: undefined,
|
||||
: existing?.boundBy,
|
||||
boundAt: now,
|
||||
lastActivityAt: now,
|
||||
};
|
||||
|
||||
Reference in New Issue
Block a user