diff --git a/CHANGELOG.md b/CHANGELOG.md index efb246185..36cbf339e 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -11,6 +11,7 @@ ### Fixes - Auto-reply: prefer `RawBody` for command/directive parsing (WhatsApp + Discord) and prevent fallback runs from clobbering concurrent session updates. (#643) — thanks @mcinteerj. +- WhatsApp: fix group reactions by preserving message IDs and sender JIDs in history; normalize participant phone numbers to JIDs in outbound reactions. (#640) — thanks @mcinteerj. - Cron: `wakeMode: "now"` waits for heartbeat completion (and retries when the main lane is busy). (#666) — thanks @roshanasingh4. - Agents/OpenAI: fix Responses tool-only → follow-up turn handling (avoid standalone `reasoning` items that trigger 400 “required following item”). - Sandbox: add `clawdbot sandbox explain` (effective policy inspector + fix-it keys); improve “sandbox jail” tool-policy/elevated errors with actionable config key paths; link to docs. @@ -41,7 +42,6 @@ - Telegram: serialize media-group processing to avoid missed albums under load. - Signal: handle `dataMessage.reaction` events (signal-cli SSE) to avoid broken attachment errors. (#637) — thanks @neist. - Docs: showcase entries for ParentPay, R2 Upload, iOS TestFlight, and Oura Health. (#650) — thanks @henrino3. - ## 2026.1.9 ### Highlights diff --git a/src/web/auto-reply.ts b/src/web/auto-reply.ts index 902db7792..5da3376c1 100644 --- a/src/web/auto-reply.ts +++ b/src/web/auto-reply.ts @@ -826,7 +826,13 @@ export async function monitorWebProvider( DEFAULT_GROUP_HISTORY_LIMIT; const groupHistories = new Map< string, - Array<{ sender: string; body: string; timestamp?: number }> + Array<{ + sender: string; + body: string; + timestamp?: number; + id?: string; + senderJid?: string; + }> >(); const groupMemberNames = new Map>(); const sleep = @@ -1104,6 +1110,8 @@ export async function monitorWebProvider( sender: string; body: string; timestamp?: number; + id?: string; + senderJid?: string; }>; suppressGroupHistoryClear?: boolean; }, @@ -1123,14 +1131,17 @@ export async function monitorWebProvider( if (historyWithoutCurrent.length > 0) { const lineBreak = "\\n"; const historyText = historyWithoutCurrent - .map((m) => - formatAgentEnvelope({ + .map((m) => { + const bodyWithId = m.id + ? `${m.body}\n[message_id: ${m.id}]` + : m.body; + return formatAgentEnvelope({ provider: "WhatsApp", from: conversationId, timestamp: m.timestamp, - body: `${m.sender}: ${m.body}`, - }), - ) + body: `${m.sender}: ${bodyWithId}`, + }); + }) .join(lineBreak); combinedBody = buildHistoryContext({ historyText, @@ -1554,11 +1565,19 @@ export async function monitorWebProvider( sender: string; body: string; timestamp?: number; + id?: string; + senderJid?: string; }>); + const sender = + msg.senderName && msg.senderE164 + ? `${msg.senderName} (${msg.senderE164})` + : (msg.senderName ?? msg.senderE164 ?? "Unknown"); history.push({ - sender: msg.senderName ?? msg.senderE164 ?? "Unknown", + sender, body: msg.body, timestamp: msg.timestamp, + id: msg.id, + senderJid: msg.senderJid, }); while (history.length > groupHistoryLimit) history.shift(); groupHistories.set(groupHistoryKey, history); diff --git a/src/web/inbound.ts b/src/web/inbound.ts index aeae8f919..87ea51d88 100644 --- a/src/web/inbound.ts +++ b/src/web/inbound.ts @@ -620,7 +620,7 @@ export async function monitorWebInbox(options: { remoteJid: jid, id: messageId, fromMe, - participant, + participant: participant ? toWhatsappJid(participant) : undefined, }, }, }); diff --git a/src/web/monitor-inbox.test.ts b/src/web/monitor-inbox.test.ts index 285de40ab..6463d5797 100644 --- a/src/web/monitor-inbox.test.ts +++ b/src/web/monitor-inbox.test.ts @@ -1402,4 +1402,36 @@ describe("web monitor inbox", () => { await listener.close(); }); + + it("normalizes participant phone numbers to JIDs in sendReaction", async () => { + const listener = await monitorWebInbox({ + verbose: false, + onMessage: vi.fn(), + accountId: ACCOUNT_ID, + authDir, + }); + const sock = await createWaSocket(); + + await listener.sendReaction( + "12345@g.us", + "msg123", + "👍", + false, + "+6421000000", + ); + + expect(sock.sendMessage).toHaveBeenCalledWith("12345@g.us", { + react: { + text: "👍", + key: { + remoteJid: "12345@g.us", + id: "msg123", + fromMe: false, + participant: "6421000000@s.whatsapp.net", + }, + }, + }); + + await listener.close(); + }); });