fix: add message deduplication to WhatsApp channel

Prevent infinite loops by tracking processed message IDs in WhatsApp
channel. The bridge may send duplicate messages which caused the bot
to respond repeatedly with the same generic message.

Changes:
- Add _processed_message_ids deque (max 2000) to track seen messages
- Skip processing if message_id was already processed
- Align WhatsApp dedup with other channels (Feishu, Email, Mochat, QQ)

This fixes the issue where WhatsApp gets stuck in a loop sending
identical responses repeatedly.

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
This commit is contained in:
spartan077
2026-02-28 13:44:22 +05:30
parent e86cfcde22
commit c0ad986504

View File

@@ -2,6 +2,7 @@
import asyncio
import json
from collections import deque
from typing import Any
from loguru import logger
@@ -21,12 +22,14 @@ class WhatsAppChannel(BaseChannel):
"""
name = "whatsapp"
MAX_PROCESSED_MESSAGE_IDS = 2000
def __init__(self, config: WhatsAppConfig, bus: MessageBus):
super().__init__(config, bus)
self.config: WhatsAppConfig = config
self._ws = None
self._connected = False
self._processed_message_ids: deque[str] = deque(maxlen=self.MAX_PROCESSED_MESSAGE_IDS)
async def start(self) -> None:
"""Start the WhatsApp channel by connecting to the bridge."""
@@ -108,6 +111,15 @@ class WhatsAppChannel(BaseChannel):
# New LID sytle typically:
sender = data.get("sender", "")
content = data.get("content", "")
message_id = data.get("id", "")
# Dedup by message ID to prevent loops
if message_id and message_id in self._processed_message_ids:
logger.debug("Duplicate message {}, skipping", message_id)
return
if message_id:
self._processed_message_ids.append(message_id)
# Extract just the phone number or lid as chat_id
user_id = pn if pn else sender
@@ -124,7 +136,7 @@ class WhatsAppChannel(BaseChannel):
chat_id=sender, # Use full LID for replies
content=content,
metadata={
"message_id": data.get("id"),
"message_id": message_id,
"timestamp": data.get("timestamp"),
"is_group": data.get("isGroup", False)
}