Aller au contenu

WhatsApp

Statut : prêt pour la production via WhatsApp Web (Baileys). Le Gateway possède les sessions liées.

  • L’intégration (openclaw onboard) et openclaw channels add --channel whatsapp vous invitent à installer le plugin WhatsApp la première fois que vous le sélectionnez.
  • openclaw channels login --channel whatsapp propose également le flux d’installation lorsque le plugin n’est pas encore présent.
  • Canal Dev + git checkout : par défaut, le chemin du plugin local.
  • Stable/Bêta : installe le plugin officiel @openclaw/whatsapp depuis ClawHub en premier, avec npm comme solution de repli.
  • Le runtime WhatsApp est distribué en dehors du package npm principal d’OpenClaw afin que les dépendances d’exécution spécifiques à WhatsApp restent avec le plugin externe.

L’installation manuelle reste disponible :

Fenêtre de terminal
openclaw plugins install clawhub:@openclaw/whatsapp

Utilisez le package nu npm (@openclaw/whatsapp) uniquement lorsque vous avez besoin du registre de repli. Épinglez une version exacte uniquement lorsque vous avez besoin d’une installation reproductible.

Appariement

La stratégie de DM par défaut est l’appariement pour les expéditeurs inconnus.

Dépannage de canal

Playbooks de diagnostic et de réparation multi-canaux.

Configuration du Gateway

Modèles et exemples complets de configuration de canal.

  1. Configurer la stratégie d'accès WhatsApp

    {
    channels: {
    whatsapp: {
    dmPolicy: "pairing",
    allowFrom: ["+15551234567"],
    groupPolicy: "allowlist",
    groupAllowFrom: ["+15551234567"],
    },
    },
    }
  2. Lier WhatsApp (QR)

    Fenêtre de terminal
    openclaw channels login --channel whatsapp
    La connexion actuelle est basée sur QR. Dans les environnements distants ou sans interface graphique, assurez-vous
    d'avoir un chemin fiable pour transmettre le code QR en direct au téléphone qui va le scanner
    avant de démarrer la connexion.
    Pour un compte spécifique :
    Fenêtre de terminal
    openclaw channels login --channel whatsapp --account work
    Pour attacher un répertoire d'authentification WhatsApp Web existant/personnalisé avant la connexion :
    Fenêtre de terminal
    openclaw channels add --channel whatsapp --account work --auth-dir /path/to/wa-auth
    openclaw channels login --channel whatsapp --account work
  3. Démarrer la passerelle

    Fenêtre de terminal
    openclaw gateway
  4. Approuver la première demande d'appariement (si vous utilisez le mode d'appariement)

    Fenêtre de terminal
    openclaw pairing list whatsapp
    openclaw pairing approve whatsapp
    Les demandes d'appariement expirent après 1 heure. Les demandes en attente sont limitées à 3 par channel.

Numéro dédié (recommandé)

C’est le mode opérationnel le plus propre :

  • identité WhatsApp séparée pour OpenClaw
  • listes d’autorisation DM et limites de routage plus claires
  • risque réduit de confusion avec les auto-discussions

Modèle de stratégie minimal :

{
channels: {
whatsapp: {
dmPolicy: "allowlist",
allowFrom: ["+15551234567"],
},
},
}
Mode de repli avec numéro personnel

Onboarding prend en charge le mode numéro personnel et écrit une ligne de base adaptée aux auto-discussions :

  • dmPolicy: "allowlist"
  • allowFrom inclut votre numéro personnel
  • selfChatMode: true

Au runtime, les protections de l’auto-discussion se basent sur le numéro auto lié et allowFrom.

Périmètre du channel WhatsApp Web uniquement

Le channel de la plateforme de messagerie est basé sur WhatsApp Web (Baileys) dans l’architecture actuelle des channels OpenClaw.

Il n’y a pas de channel de messagerie WhatsApp Twilio séparé dans le registre des channels de chat intégrés.

  • Le Gateway possède le socket WhatsApp et la boucle de reconnexion.
  • Le chien de garde de reconnexion utilise l’activité de transport WhatsApp Web, et pas seulement le volume des messages entrants de l’application ; ainsi, une session d’appareil lié silencieuse n’est pas redémarrée uniquement parce que personne n’a envoyé de message récemment. Un plafond de silence d’application plus long force toujours une reconnexion si les trames de transport continuent d’arriver mais qu’aucun message d’application n’est géré pendant la fenêtre du chien de garde ; après une reconnexion transitoire pour une session récemment active, cette vérification de silence d’application utilise le délai d’expiration normal des messages pour la première fenêtre de récupération.
  • Les timings du socket Baileys sont explicites sous web.whatsapp.* : keepAliveIntervalMs contrôle les pings d’application WhatsApp Web, connectTimeoutMs contrôle le délai d’expiration de la poignée de main d’ouverture, et defaultQueryTimeoutMs contrôle les délais d’expiration des requêtes Baileys.
  • Les envois sortants nécessitent un écouteur WhatsApp actif pour le compte cible.
  • Les envois de groupe attachent des métadonnées de mention natives pour les jetons @+<digits> et @<digits> dans le texte et les légendes des médias lorsque le jeton correspond aux métadonnées du participant WhatsApp actuel, y compris les groupes pris en charge par LID.
  • Les discussions de statut et de diffusion sont ignorées (@status, @broadcast).
  • Le chien de garde de reconnexion suit l’activité de transport WhatsApp Web, et pas seulement le volume des messages entrants de l’application : les sessions d’appareil lié silencieuses restent actives tant que les trames de transport continuent, mais un arrêt du transport force une reconnexion bien avant le chemin de déconnexion distant ultérieur.
  • Les discussions directes utilisent les règles de session DM (session.dmScope ; par défaut, main réduit les DMs à la session principale de l’agent).
  • Les sessions de groupe sont isolées (agent:<agentId>:whatsapp:group:<jid>).
  • Les chaînes/lettres d’information WhatsApp peuvent être des cibles sortantes explicites avec leur JID natif @newsletter. Les envois de lettres d’information sortants utilisent les métadonnées de session de chaîne (agent:<agentId>:whatsapp:channel:<jid>) plutôt que la sémantique de session DM.
  • Le transport WhatsApp Web respecte les variables d’environnement de proxy standard sur l’hôte de la passerelle (WhatsAppHTTPS_PROXY, HTTP_PROXY, NO_PROXYWhatsApp / variantes en minuscules). Préférez la configuration proxy au niveau de l’hôte aux paramètres de proxy WhatsApp spécifiques au canal.
  • Lorsque messages.removeAckAfterReplyOpenClawWhatsApp est activé, OpenClaw efface la réaction d’accusé de réception (ack) WhatsApp une fois qu’une réponse visible est délivrée.

WhatsApp peut afficher les prompts d’approbation d’exécution et de plugin avec des réactions 👍 / 👎. La livraison est contrôlée par la configuration de transfert d’approbation de premier niveau :

{
approvals: {
exec: {
enabled: true,
mode: "session",
},
plugin: {
enabled: true,
mode: "targets",
targets: [{ channel: "whatsapp", to: "+15551234567" }],
},
},
}

approvals.exec et approvals.plugin sont indépendants. L’activation de WhatsApp en tant que channel ne fait que lier le transport ; elle n’envoie pas de invites d’approbation, sauf si la famille d’approbation correspondante est activée et routée vers WhatsApp. Le mode session délivre des approbations par emoji natives uniquement pour les approbations qui proviennent de WhatsApp. Le mode cible utilise le pipeline de transfert partagé pour les cibles WhatsApp explicites et ne crée pas de ventilateur de DM d’approbateur séparé.

Les réactions d’approbation WhatsApp nécessitent des approbateurs WhatsApp explicites provenant de allowFrom ou "*". defaultTo contrôle les cibles de message par défaut ordinaires ; ce n’est pas un approbateur d’approbation. Les commandes manuelles /approve passent toujours par le chemin d’autorisation d’envoi WhatsApp normal avant la résolution de l’approbation.

Les messages entrants WhatsApp peuvent contenir du contenu de message personnel, des numéros de téléphone, des identifiants de groupe, des noms d’expéditeur et des champs de corrélation de session. Pour cette raison, WhatsApp ne diffuse pas les charges utiles de hook message_received entrantes aux plugins sauf si vous optez explicitement pour :

{
channels: {
whatsapp: {
pluginHooks: {
messageReceived: true,
},
},
},
}

Vous pouvez limiter l’opt-in à un seul compte :

{
channels: {
whatsapp: {
accounts: {
work: {
pluginHooks: {
messageReceived: true,
},
},
},
},
},
}

N’activez cela que pour les plugins auxquels vous faites confiance pour recevoir le contenu et les identifiants des messages WhatsApp entrants.

channels.whatsapp.dmPolicy contrôle l’accès aux discussions directes :

  • pairing (par défaut)
  • allowlist
  • open (nécessite que allowFrom inclue "*")
  • disabled

allowFrom accepte les numéros au format E.164 (normalisés en interne).

allowFrom est une liste de contrôle d’accès des expéditeurs de DM. Elle ne bloque pas les envois sortants explicites vers les JID de groupe WhatsApp ou les JID de channel @newsletter.

Substitution multi-compte : `channels.whatsapp.accounts.

.dmPolicy(etallowFrom`) priment sur les paramètres par défaut au niveau du channel pour ce compte.

Détails du comportement à l'exécution :
- les appariements sont conservés dans le magasin d'autorisation de channel et fusionnés avec `allowFrom` configuré
- l'automatisation planifiée et le destinataire de secours du heartbeat utilisent des cibles de livraison explicites ou `allowFrom` configuré ; les approbations d'appariement DM ne sont pas des destinataires implicites pour le cron ou le heartbeat
- si aucune liste d'autorisation n'est configurée, le numéro personnel lié est autorisé par défaut
- OpenClaw n'apparie jamais automatiquement les DM sortants `fromMe` (messages que vous vous envoyez depuis l'appareil lié)

Comportement du numéro personnel et de l’auto-discussion

Section intitulée « Comportement du numéro personnel et de l’auto-discussion »

Lorsque le numéro personnel lié est également présent dans allowFromWhatsApp, les sauvegardes d’auto-discussion WhatsApp s’activent :

  • ignorer les accusés de lecture pour les tours de chat avec soi-même
  • ignorer le comportement de déclenchement automatique de mention-JID qui vous ferait autrement vous pinguer vous-même
  • si messages.responsePrefix n’est pas défini, les réponses de chat avec soi-même correspondent par défaut à [{identity.name}] ou [openclaw]
Enveloppe entrante + contexte de réponse

Les messages WhatsApp entrants sont enveloppés dans l’enveloppe entrante partagée.

Si une réponse citée existe, le contexte est ajouté sous cette forme :

[Replying to

id:

]

[/Replying]

Les champs de métadonnées de réponse sont également renseignés lorsque disponibles (`ReplyToId`, `ReplyToBody`, `ReplyToSender`, JID de l'expéditeur/E.164).
Lorsque la cible de la réponse citée est un média téléchargeable, OpenClaw l'enregistre via
le magasin de médias entrant normal et l'expose en tant que `MediaPath`/`MediaType` afin
que l'agent puisse inspecter l'image référencée au lieu de ne voir que
`

`.

Espaces réservés pour les médias et extraction de localisation/contact

Les messages entrants contenant uniquement des médias sont normalisés avec des espaces réservés tels que :

  • `

-

-

-

-

`

Les notes vocales autorisées des groupes sont transcrites avant le filtrage par mention lorsque le
corps est uniquement `

`, de sorte que prononcer la mention du bot dans la note vocale peut déclencher la réponse. Si la transcription ne mentionne toujours pas le bot, la transcription est conservée dans l’historique des groupes en attente au lieu de l’espace réservé brut.

Les corps de localisation utilisent un texte de coordonnées concis. Les étiquettes/commentaires de localisation et les détails de contact/vCard sont rendus en tant que métadonnées non fiables clôturées, et non en tant que texte d'invite en ligne.
Injection de l'historique de groupe en attente

Pour les groupes, les messages non traités peuvent être mis en tampon et injectés en contexte lorsque le bot est finalement déclenché.

  • limite par défaut : 50
  • configuration : channels.whatsapp.historyLimit
  • repli : messages.groupChat.historyLimit
  • 0 désactive

Marqueurs d’injection :

  • [Chat messages since your last reply - for context]
  • [Current message - respond to this]
Accusés de réception

Les accusés de réception sont activés par défaut pour les messages WhatsApp entrants acceptés.

Désactiver globalement :

{
channels: {
whatsapp: {
sendReadReceipts: false,
},
},
}

Remplacement par compte :

{
channels: {
whatsapp: {
accounts: {
work: {
sendReadReceipts: false,
},
},
},
},
}

Les tours de dialogue avec soi-même ignorent les accusés de réception même s’ils sont activés globalement.

Découpage du texte
  • limite de découpage par défaut : channels.whatsapp.textChunkLimit = 4000
  • channels.whatsapp.chunkMode = "length" | "newline"
  • le mode newline préfère les limites de paragraphe (lignes vides), puis revient au découpage sécurisé en termes de longueur
Comportement des médias sortants
  • prend en charge les charges utiles d’image, vidéo, audio (note vocale PTT) et de document
  • les médias audio sont envoyés via la charge utile audio de Baileys avec ptt: true, de sorte que les clients WhatsApp l’affichent comme une note vocale appuyer-parler (push-to-talk)
  • les charges utiles de réponse préservent audioAsVoice; la sortie de note vocale TTS pour WhatsApp reste sur ce chemin PTT même lorsque le provider renvoie du MP3 ou WebM
  • l’audio Ogg/Opus natif est envoyé sous forme de audio/ogg; codecs=opus pour la compatibilité des notes vocales
  • l’audio non-Ogg, y compris la sortie MP3/WebM du TTS Microsoft Edge, est transcodé avec ffmpeg en Ogg/Opus mono 48 kHz avant la livraison PTT
  • /tts latest envoie la dernière réponse de l’assistant en une seule note vocale et supprime les envois répétés pour la même réponse; /tts chat on|off|default contrôle le TTS automatique pour la discussion WhatsApp actuelle
  • la lecture des GIF animés est prise en charge via gifPlayback: true lors de l’envoi de vidéos
  • forceDocument / asDocument envoie les images, GIF et vidéos sortants via la charge utile de document Baileys pour éviter la compression des médias WhatsApp tout en préservant le nom de fichier résolu et le type MIME
  • les légendes sont appliquées au premier élément multimédia lors de l’envoi de charges utiles de réponse multimédia, sauf que les notes vocales PTT envoient d’abord l’audio puis le texte visible séparément, car les clients WhatsApp n’affichent pas les légendes de notes vocales de manière cohérente
  • la source multimédia peut être HTTP(S), file://, ou des chemins locaux
Limites de taille des médias et comportement de repli
  • limite d’enregistrement des médias entrants : channels.whatsapp.mediaMaxMb (par défaut 50)
  • limite d’envoi des médias sortants : channels.whatsapp.mediaMaxMb (par défaut 50)
  • les remplacements par compte utilisent `channels.whatsapp.accounts.

.mediaMaxMb - les images sont automatiquement optimisées (redimensionnement/ajustement de la qualité) pour respecter les limites, sauf siforceDocument/asDocument` demande une livraison de document - en cas d’échec de l’envoi d’un média, le repli du premier élément envoie un avertissement texte au lieu d’abandonner silencieusement la réponse

WhatsApp prend en charge la citation de réponse native, où les réponses sortantes citent visuellement le message entrant. Contrôlez cela avec channels.whatsapp.replyToMode.

ValeurComportement
"off"Ne jamais citer ; envoyer comme un message simple
"first"Citer uniquement le premier bloc de réponse sortant
"all"Citer chaque bloc de réponse sortant
"batched"Citer les réponses groupées en file d’attente tout en laissant les réponses immédiates sans citation

La valeur par défaut est "off". Les remplacements par compte utilisent channels.whatsapp.accounts.<id>.replyToMode.

{
channels: {
whatsapp: {
replyToMode: "first",
},
},
}

channels.whatsapp.reactionLevel contrôle la manière dont l’agent utilise les réactions emoji sur WhatsApp :

NiveauRéactions d’accusé de réceptionRéactions initiées par l’agentDescription
"off"NonNonAucune réaction
"ack"OuiNonRéactions d’accusé de réception uniquement (accusé de réception avant réponse)
"minimal"OuiOui (conservateur)Accusé de réception + réactions de l’agent avec directives conservatrices
"extensive"OuiOui (encouragé)Accusé de réception + réactions de l’agent avec directives encourageantes

Par défaut : "minimal".

Les remplacements par compte utilisent channels.whatsapp.accounts.<id>.reactionLevel.

{
channels: {
whatsapp: {
reactionLevel: "ack",
},
},
}

WhatsApp prend en charge les réactions d’accusé de réception immédiats sur la réception entrante via WhatsAppchannels.whatsapp.ackReaction. Les réactions d’accusé de réception sont contrôlées par reactionLevel — elles sont supprimées lorsque reactionLevel est "off".

{
channels: {
whatsapp: {
ackReaction: {
emoji: "👀",
direct: true,
group: "mentions", // always | mentions | never
},
},
},
}

Notes de comportement :

  • envoyé immédiatement après acceptation de l’entrant (pré-réponse)
  • si ackReaction est présent sans emoji, WhatsApp utilise l’émoji d’identité de l’agent acheminé, par défaut « 👀 » ; omettez ackReaction ou définissez emoji: "" pour n’envoyer aucune réaction d’accusé de réception
  • les échecs sont enregistrés mais ne bloquent pas la livraison des réponses normales
  • le mode de groupe mentions réagit aux tours déclenchés par des mentions ; l’activation de groupe always agit comme une dérogation pour cette vérification
  • WhatsApp utilise channels.whatsapp.ackReaction (l’ancien messages.ackReaction n’est pas utilisé ici)

Définissez messages.statusReactions.enabled: true pour permettre à WhatsApp de remplacer la réaction d’accusé de réception pendant un tour au lieu de laisser un émoji de reçu statique. Lorsqu’elle est activée, OpenClaw utilise le même emplacement de réaction aux messages entrants pour les états du cycle de vie tels que mis en file d’attente, réflexion, activité de l’outil, compactage, terminé et erreur.

{
messages: {
statusReactions: {
enabled: true,
emojis: {
deploy: "🛫",
build: "🏗️",
concierge: "💁",
},
},
},
}

Notes sur le comportement :

  • channels.whatsapp.ackReaction contrôle toujours si les réactions de statut sont éligibles pour les messages directs et les groupes.
  • La réaction de statut mis en file d’attente utilise le même émoji d’accusé de réception effectif que les réactions d’accusé de réception simples.
  • WhatsApp dispose d’un seul emplacement de réaction de bot par message, les mises à jour du cycle de vie remplacent donc la réaction actuelle sur place.
  • messages.removeAckAfterReply: true efface la réaction de statut finale après la pause configurée pour terminé/erreur.
  • Les catégories d’émojis d’outils incluent tool, coding, web, deploy, build et concierge.
Sélection de compte et valeurs par défaut
  • les identifiants de compte proviennent de channels.whatsapp.accounts
  • sélection du compte par défaut : default si présent, sinon le premier identifiant de compte configuré (trié)
  • les identifiants de compte sont normalisés en interne pour la recherche
Chemins d'accès aux identifiants et compatibilité avec l'ancien système
  • chemin d’authentification actuel : `~/.openclaw/credentials/whatsapp/

/creds.json - fichier de sauvegarde :creds.json.bak - l'authentification par défaut héritée dans~/.openclaw/credentials/` est toujours reconnue/migrée pour les flux de comptes par défaut

Comportement de déconnexion

`openclaw channels logout —channel whatsapp [—account

]`WhatsAppGatewayWhatsApp efface l’état d’authentification WhatsApp pour ce compte.

Lorsqu'un Gateway est accessible, la déconnexion arrête d'abord l'écouteur WhatsApp en direct pour le compte sélectionné afin que la session liée ne continue pas à recevoir des messages jusqu'au prochain redémarrage. `openclaw channels remove --channel whatsapp` arrête également l'écouteur en direct avant de désactiver ou de supprimer la configuration du compte.
Dans les répertoires d'authentification hérités, `oauth.json`Baileys est conservé tandis que les fichiers d'authentification Baileys sont supprimés.
  • La prise en charge des outils de l’agent inclut l’action de réaction WhatsApp (WhatsAppreact).
  • Portes d’action (Action gates) :
    • channels.whatsapp.actions.reactions
    • channels.whatsapp.actions.polls
  • Les écritures de configuration initiées par le canal sont activées par défaut (désactiver via channels.whatsapp.configWrites=false).
Non lié (QR requis)

Symptôme : l’état du canal indique non lié.

Correction :

Fenêtre de terminal
openclaw channels login --channel whatsapp
openclaw channels status
Linked but disconnected / reconnect loop

Symptôme : compte lié avec des déconnexions répétées ou des tentatives de reconnexion.

Les comptes inactifs peuvent rester connectés au-delà du délai d’expiration normal des messages ; le watchdog redémarre lorsque l’activité de transport de WhatsApp Web s’arrête, que la socket se ferme ou que l’activité au niveau de l’application reste silencieuse au-delà de la fenêtre de sécurité étendue.

Si les journaux montrent des status=408 Request Time-out Connection was lostBaileys répétés, ajustez les timings de socket de Baileys sous web.whatsapp. Commencez par raccourcir keepAliveIntervalMs en dessous du délai d’inactivité de votre réseau et en augmentant connectTimeoutMs sur les liaisons lentes ou perturbées :

{
web: {
whatsapp: {
keepAliveIntervalMs: 15000,
connectTimeoutMs: 60000,
defaultQueryTimeoutMs: 60000,
},
},
}

Correction :

Fenêtre de terminal
openclaw channels status --probe
openclaw doctor
openclaw logs --follow
openclaw gateway status

Si la boucle persiste après la correction de la connectivité de l’hôte et des timings, sauvegardez le répertoire d’authentification du compte et reliez ce compte :

Fenêtre de terminal
cp -a ~/.openclaw/credentials/whatsapp/


~/.openclaw/credentials/whatsapp/

.bak openclaw channels logout —channel whatsapp —account

openclaw channels login —channel whatsapp —account

Si `~/.openclaw/logs/whatsapp-health.log` indique `Gateway inactive` mais que `openclaw gateway status` et `openclaw channels status --probe`WhatsApp montrent que la passerelle et WhatsApp sont en bonne santé, exécutez `openclaw doctor`Linux. Sur Linux, le docteur avertit concernant les entrées crontab héritées qui appellent encore `~/.openclaw/bin/ensure-whatsapp.sh` ; supprimez ces entrées obsolètes avec `crontab -e` car cron peut manquer de l'environnement utilisateur de systemd et faire rapporter de manière incorrecte l'état de la passerelle par cet ancien script.
Si nécessaire, reliez avec `channels login`.
QR login times out behind a proxy

Symptôme : openclaw channels login --channel whatsapp échoue avant d’afficher un code QR utilisable avec status=408 Request Time-outWhatsApp ou une déconnexion de socket TLS.

La connexion WhatsApp Web utilise l’environnement proxy standard de l’hôte de la passerelle (HTTPS_PROXY, HTTP_PROXY, variantes en minuscules et NO_PROXY). Vérifiez que le processus de la passerelle hérite de l’environnement proxy et que NO_PROXY ne correspond pas à mmg.whatsapp.net.

No active listener when sending

Les envois sortants échouent rapidement lorsqu’aucun écouteur de passerelle actif n’existe pour le compte cible.

Assurez-vous que la passerelle est en cours d’exécution et que le compte est lié.

<Accordion title=“WhatsAppReply appears in transcript but not in WhatsApp”WhatsAppOpenClawBaileysWhatsApp> Les lignes de la transcription enregistrent ce que l’agent a généré. La livraison WhatsApp est vérifiée séparément : OpenClaw ne considère une réponse automatique comme envoyée qu’après que Baileys a renvoyé un ID de message sortant pour au moins un envoi de texte ou de média visible.

Les réactions d'accusé de réception sont des reçus indépendants précédant la réponse. Une réaction réussie ne prouve pas que la réponse textuelle ou média ultérieure a été acceptée par WhatsApp.
Vérifiez les journaux de la passerelle pour `auto-reply delivery failed` ou `auto-reply was not accepted by WhatsApp provider`.
Group messages unexpectedly ignored

Vérifiez dans cet ordre :

  • groupPolicy
  • groupAllowFrom / allowFrom
  • entrées de la liste d’autorisation groups
  • filtrage par mentions (requireMention + modèles de mentions)
  • clés en double dans openclaw.json (JSON5) : les entrées ultérieures écrasent les précédentes, gardez donc un seul groupPolicy par portée

Si channels.whatsapp.groupsWhatsAppOpenClaw est présent, WhatsApp peut toujours observer les messages d’autres groupes, mais OpenClaw les ignore avant le routage de session. Ajoutez le JID du groupe à channels.whatsapp.groups ou ajoutez groups["*"] pour admettre tous les groupes tout en maintenant l’autorisation de l’expéditeur sous groupPolicy et groupAllowFrom.

<Accordion title=“BunBun runtime warning”WhatsAppBunWhatsAppTelegram> L’exécution de la passerelle WhatsApp doit utiliser Node. Bun est signalé comme incompatible pour le fonctionnement stable des passerelles WhatsApp/Telegram.

WhatsApp prend en charge les invites du système de style Telegram pour les groupes et les discussions directes via les cartes groups et direct.

Hiérarchie de résolution pour les messages de groupe :

La carte groups effective est déterminée en premier : si le compte définit sa propre groups, elle remplace entièrement la carte groups racine (pas de fusion profonde). La recherche d’invite s’exécute ensuite sur la carte unique résultante :

  1. Invite du système spécifique au groupe (groups["<groupId>"].systemPrompt) : utilisée lorsque l’entrée spécifique au groupe existe dans la carte et que sa clé systemPrompt est définie. Si systemPrompt est une chaîne vide (""), le caractère générique est supprimé et aucune invite du système n’est appliquée.
  2. Invite du système générique pour les groupes (groups["*"].systemPrompt) : utilisée lorsque l’entrée spécifique au groupe est totalement absente de la carte, ou lorsqu’elle existe mais ne définit aucune clé systemPrompt.

Hiérarchie de résolution pour les messages directs :

La carte direct effective est déterminée en premier : si le compte définit sa propre direct, elle remplace entièrement la carte direct racine (pas de fusion profonde). La recherche d’invite s’exécute ensuite sur la carte unique résultante :

  1. Invite du système spécifique au direct (direct["<peerId>"].systemPrompt) : utilisée lorsque l’entrée spécifique au pair existe dans la carte et que sa clé systemPrompt est définie. Si systemPrompt est une chaîne vide (""), le caractère générique est supprimé et aucune invite du système n’est appliquée.
  2. Invite du système générique pour les directs (direct["*"].systemPrompt) : utilisée lorsque l’entrée spécifique au pair est totalement absente de la carte, ou lorsqu’elle existe mais ne définit aucune clé systemPrompt.

Différence avec le comportement multi-compte Telegram : Sur Telegram, le TelegramTelegramgroups racine est intentionnellement supprimé pour tous les comptes dans une configuration multi-compte — même les comptes qui ne définissent pas leur propre groupsWhatsApp — pour empêcher un bot de recevoir des messages de groupe pour les groupes auxquels il n’appartient pas. WhatsApp n’applique pas cette garde : le groups racine et le directWhatsApp racine sont toujours hérités par les comptes qui ne définissent pas de substitution au niveau du compte, quel que soit le nombre de comptes configurés. Dans une configuration WhatsApp multi-compte, si vous souhaitez des invites de groupe ou directes par compte, définissez la carte complète sous chaque compte explicitement plutôt que de vous fier aux valeurs par défaut au niveau racine.

Comportement important :

  • channels.whatsapp.groups est à la fois une carte de configuration par groupe et la liste d’autorisation de groupe au niveau du chat. Soit au niveau racine soit au niveau du compte, groups["*"] signifie « tous les groupes sont admis » pour cette portée.
  • N’ajoutez un groupe générique systemPrompt que lorsque vous souhaitez déjà que cette portée admette tous les groupes. Si vous souhaitez toujours qu’un ensemble fixe d’ID de groupe soient éligibles, n’utilisez pas groups["*"] pour l’invite par défaut. À la place, répétez l’invite sur chaque entrée de groupe explicitement autorisée.
  • L’admission de groupe et l’autorisation de l’expéditeur sont des contrôles distincts. groups["*"] élargit l’ensemble des groupes qui peuvent atteindre la gestion de groupe, mais il n’autorise pas par lui-même chaque expéditeur dans ces groupes. L’accès de l’expéditeur est toujours contrôlé séparément par channels.whatsapp.groupPolicy et channels.whatsapp.groupAllowFrom.
  • channels.whatsapp.direct n’a pas le même effet secondaire pour les DMs. direct["*"] fournit uniquement une configuration de chat direct par défaut après qu’un DM a déjà été admis par dmPolicy plus allowFrom ou les règles du magasin d’appairage.

Exemple :

{
channels: {
whatsapp: {
groups: {
// Use only if all groups should be admitted at the root scope.
// Applies to all accounts that do not define their own groups map.
"*": { systemPrompt: "Default prompt for all groups." },
},
direct: {
// Applies to all accounts that do not define their own direct map.
"*": { systemPrompt: "Default prompt for all direct chats." },
},
accounts: {
work: {
groups: {
// This account defines its own groups, so root groups are fully
// replaced. To keep a wildcard, define "*" explicitly here too.
requireMention: false,
systemPrompt: "Focus on project management.",
},
// Use only if all groups should be admitted in this account.
"*": { systemPrompt: "Default prompt for work groups." },
},
direct: {
// This account defines its own direct map, so root direct entries are
// fully replaced. To keep a wildcard, define "*" explicitly here too.
"+15551234567": { systemPrompt: "Prompt for a specific work direct chat." },
"*": { systemPrompt: "Default prompt for work direct chats." },
},
},
},
},
},
}

Référence principale :

Champs WhatsApp à fort signal :

  • accès : dmPolicy, allowFrom, groupPolicy, groupAllowFrom, groups
  • livraison : textChunkLimit, chunkMode, mediaMaxMb, sendReadReceipts, ackReaction, reactionLevel
  • multi-compte : accounts.<id>.enabled, accounts.<id>.authDir, substitutions au niveau du compte
  • opérations : configWrites, debounceMs, web.enabled, web.heartbeatSeconds, web.reconnect.*, web.whatsapp.*
  • comportement de la session : session.dmScope, historyLimit, dmHistoryLimit, dms.<id>.historyLimit
  • invites : groups.<id>.systemPrompt, groups["*"].systemPrompt, direct.<id>.systemPrompt, direct["*"].systemPrompt