diff --git a/CHANGELOG.md b/CHANGELOG.md index 988b97f1972..3527559b715 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -38,6 +38,7 @@ Docs: https://docs.openclaw.ai - Agents/Anthropic: ignore non-positive Anthropic Messages token overrides and fail locally when no positive token budget remains, so invalid `max_tokens` values no longer reach the provider API. (#66664) thanks @jalehman - Agents/context engines: preserve prompt-only token counts, not full request totals, when deferred maintenance reuses after-turn runtime context so background compaction bookkeeping matches the active prompt window. (#66820) thanks @jalehman. - BlueBubbles/inbound: add a persistent file-backed GUID dedupe so MessagePoller webhook replays after BB Server restart or reconnect no longer cause the agent to re-reply to already-handled messages. (#19176, #12053, #66816) Thanks @omarshahine. +- Gateway/tests: keep the built-in `imsg` agent alias regression on the stubbed iMessage path and harden shared gateway WS request helpers against reply-listener races so the alias contract no longer flakes in CI. Thanks @vincentkoc. - Secrets/plugins/status: align SecretRef inspect-vs-strict handling across plugin preload, read-only status/agents surfaces, and runtime auth paths so unresolved refs no longer crash read-only CLI flows while runtime-required non-env refs stay strict. (#66818) Thanks @joshavant. - Memory/dreaming: stop ordinary transcripts that merely quote the dream-diary prompt from being classified as internal dreaming runs and silently dropped from session recall ingestion. (#66852) Thanks @gumadeiras. - Telegram/documents: sanitize binary reply context and ZIP-like archive extraction so `.epub` and `.mobi` uploads can no longer leak raw binary into prompt context through reply metadata or archive-to-`text/plain` coercion. (#66877) Thanks @martinfrancois. diff --git a/src/gateway/server.agent.gateway-server-agent-b.test.ts b/src/gateway/server.agent.gateway-server-agent-b.test.ts index 8add6559e4b..67293eb25d1 100644 --- a/src/gateway/server.agent.gateway-server-agent-b.test.ts +++ b/src/gateway/server.agent.gateway-server-agent-b.test.ts @@ -225,6 +225,11 @@ describe("gateway server agent", () => { test("agent accepts built-in channel alias (imsg)", async () => { const registry = createRegistry([ + { + pluginId: "imessage", + source: "test", + plugin: createStubChannelPlugin({ id: "imessage", label: "iMessage" }), + }, { pluginId: "msteams", source: "test", @@ -245,7 +250,9 @@ describe("gateway server agent", () => { idempotencyKey: "idem-agent-imsg", }); expect(resIMessage.ok).toBe(true); - + await vi.waitFor(() => { + expect(vi.mocked(agentCommand)).toHaveBeenCalled(); + }); expectAgentRoutingCall({ channel: "imessage", deliver: true, fromEnd: 1 }); }); diff --git a/src/gateway/test-helpers.server.ts b/src/gateway/test-helpers.server.ts index 90084ba9ee2..cff85371b1b 100644 --- a/src/gateway/test-helpers.server.ts +++ b/src/gateway/test-helpers.server.ts @@ -944,6 +944,14 @@ export async function connectReq( nonce: connectChallengeNonce, }; })(); + const isResponseForId = (o: unknown): boolean => { + if (!o || typeof o !== "object" || Array.isArray(o)) { + return false; + } + const rec = o as Record; + return rec.type === "res" && rec.id === id; + }; + const responsePromise = onceMessage(ws, isResponseForId, opts?.timeoutMs); ws.send( JSON.stringify({ type: "req", @@ -971,14 +979,7 @@ export async function connectReq( }, }), ); - const isResponseForId = (o: unknown): boolean => { - if (!o || typeof o !== "object" || Array.isArray(o)) { - return false; - } - const rec = o as Record; - return rec.type === "res" && rec.id === id; - }; - return await onceMessage(ws, isResponseForId, opts?.timeoutMs); + return await responsePromise; } export async function connectOk(ws: WebSocket, opts?: Parameters[1]) { @@ -1042,8 +1043,7 @@ export async function rpcReq>( clearSessionStoreCacheForTest(); const { randomUUID } = await import("node:crypto"); const id = randomUUID(); - ws.send(JSON.stringify({ type: "req", id, method, params })); - return await onceMessage<{ + const responsePromise = onceMessage<{ type: "res"; id: string; ok: boolean; @@ -1060,6 +1060,8 @@ export async function rpcReq>( }, timeoutMs, ); + ws.send(JSON.stringify({ type: "req", id, method, params })); + return await responsePromise; } export async function waitForSystemEvent(timeoutMs = 2000) {