@openclaw/whatsapp 2026.6.10 → 2026.6.11-beta.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (34) hide show
  1. package/dist/{access-control-BnFVCHHH.js → access-control-_oQx0_UZ.js} +2 -2
  2. package/dist/{action-runtime-ClQLHIwf.js → action-runtime-D-FTwc8j.js} +1 -1
  3. package/dist/action-runtime-api.js +1 -1
  4. package/dist/action-runtime.runtime.js +1 -1
  5. package/dist/api.js +8 -8
  6. package/dist/{approval-handler.runtime-DLjPf_Mx.js → approval-handler.runtime-DNBh4thG.js} +1 -1
  7. package/dist/{auth-store-RyuCPHE0.js → auth-store-BRv2o3w2.js} +2 -2
  8. package/dist/{channel-CNA0E9wp.js → channel-C9zebxrw.js} +9 -11
  9. package/dist/channel-plugin-api.js +1 -1
  10. package/dist/{channel-react-action-CdYJKJWb.js → channel-react-action-C56UzM_r.js} +2 -2
  11. package/dist/{channel.runtime-ZKS2C0Cw.js → channel.runtime-kVF_UONw.js} +4 -4
  12. package/dist/{channel.setup-BfcLCLNn.js → channel.setup-BTi6IdDT.js} +2 -2
  13. package/dist/{connection-controller-BDuM0Kc7.js → connection-controller-Ds4puj_n.js} +7 -5
  14. package/dist/contract-api.js +1 -1
  15. package/dist/{identity-Cm6bKAtk.js → identity-DdeafYji.js} +1 -1
  16. package/dist/light-runtime-api.js +1 -1
  17. package/dist/{login-B503Fwb8.js → login-FpqysWi0.js} +3 -3
  18. package/dist/{login-qr-AgwdQyj_.js → login-qr-BjfpyyN0.js} +3 -3
  19. package/dist/login-qr-runtime.js +1 -1
  20. package/dist/{monitor-C5_QBO1-.js → monitor-BVD90YEd.js} +135 -15
  21. package/dist/{quoted-message-DVOfpEja.js → quoted-message-DqmWlbN7.js} +1 -1
  22. package/dist/runtime-api.js +7 -7
  23. package/dist/{send-A9EqsNyz.js → send-BplHdEjw.js} +40 -8
  24. package/dist/{send-api-89SE5WKV.js → send-api-11yoHJhM.js} +4 -4
  25. package/dist/{session-BW8RcCcb.js → session-DlHpYSAl.js} +4 -2
  26. package/dist/{setup-core-DVEkfMVh.js → setup-core-D0JxJ53T.js} +2 -2
  27. package/dist/{setup-finalize-DJepnx7S.js → setup-finalize-BRTq3uPs.js} +2 -2
  28. package/dist/setup-plugin-api.js +1 -1
  29. package/dist/{setup-surface-ByAUWXyq.js → setup-surface-BpdIDwDg.js} +2 -2
  30. package/dist/{text-runtime-BBSmIBHN.js → text-runtime-CpiloI73.js} +53 -1
  31. package/npm-shrinkwrap.json +3 -3
  32. package/openclaw.plugin.json +4 -0
  33. package/package.json +6 -5
  34. package/skills/wacli/SKILL.md +72 -0
@@ -1,6 +1,6 @@
1
1
  import { a as resolveWhatsAppAccount } from "./accounts-DgViSyJx.js";
2
- import { l as isSelfChatMode, n as normalizeE164 } from "./text-runtime-BBSmIBHN.js";
3
- import { a as getSelfIdentity, o as getSenderIdentity } from "./identity-Cm6bKAtk.js";
2
+ import { l as isSelfChatMode, n as normalizeE164 } from "./text-runtime-CpiloI73.js";
3
+ import { a as getSelfIdentity, o as getSenderIdentity } from "./identity-DdeafYji.js";
4
4
  import { defaultRuntime } from "openclaw/plugin-sdk/runtime-env";
5
5
  import { resolveChannelGroupPolicy, resolveChannelGroupRequireMention } from "openclaw/plugin-sdk/channel-policy";
6
6
  import { createChannelPairingChallengeIssuer } from "openclaw/plugin-sdk/channel-pairing";
@@ -1,6 +1,6 @@
1
1
  import { a as resolveWhatsAppAccount } from "./accounts-DgViSyJx.js";
2
2
  import { t as resolveWhatsAppOutboundTarget } from "./resolve-outbound-target-CcdugbDf.js";
3
- import { g as resolveWhatsAppReactionLevel, r as sendReactionWhatsApp } from "./send-A9EqsNyz.js";
3
+ import { g as resolveWhatsAppReactionLevel, r as sendReactionWhatsApp } from "./send-BplHdEjw.js";
4
4
  import { ToolAuthorizationError, createActionGate, jsonResult, readReactionParams, readStringParam } from "openclaw/plugin-sdk/channel-actions";
5
5
  //#region extensions/whatsapp/src/action-runtime-target-auth.ts
6
6
  function resolveAuthorizedWhatsAppOutboundTarget(params) {
@@ -1,2 +1,2 @@
1
- import { t as handleWhatsAppAction } from "./action-runtime-ClQLHIwf.js";
1
+ import { t as handleWhatsAppAction } from "./action-runtime-D-FTwc8j.js";
2
2
  export { handleWhatsAppAction };
@@ -1,2 +1,2 @@
1
- import { t as handleWhatsAppAction } from "./action-runtime-ClQLHIwf.js";
1
+ import { t as handleWhatsAppAction } from "./action-runtime-D-FTwc8j.js";
2
2
  export { handleWhatsAppAction };
package/dist/api.js CHANGED
@@ -2,20 +2,20 @@ import { r as resolveDefaultWhatsAppAccountId, t as listAccountIds } from "./acc
2
2
  import { a as resolveWhatsAppAccount, i as listWhatsAppAuthDirs, n as hasAnyWhatsAppAuth, o as resolveWhatsAppAuthDir, r as listEnabledWhatsAppAccounts, s as resolveWhatsAppMediaMaxBytes, t as DEFAULT_WHATSAPP_MEDIA_MAX_MB } from "./accounts-DgViSyJx.js";
3
3
  import { a as normalizeWhatsAppAllowFromEntries, c as normalizeWhatsAppTarget, i as looksLikeWhatsAppTargetId, r as isWhatsAppUserTarget, s as normalizeWhatsAppMessagingTarget, t as isWhatsAppGroupJid } from "./normalize-target-bVWjgftN.js";
4
4
  import { t as resolveWhatsAppOutboundTarget } from "./resolve-outbound-target-CcdugbDf.js";
5
- import "./send-A9EqsNyz.js";
5
+ import "./send-BplHdEjw.js";
6
6
  import { n as getStatusCode, t as formatError } from "./session-errors-CbsoQqoy.js";
7
7
  import { n as createWhatsAppSocketOperationTimeoutAdapter, t as DEFAULT_WHATSAPP_SOCKET_TIMING } from "./socket-timing-DvMNkIge.js";
8
- import { c as assertWebChannel, d as markdownToWhatsApp, f as resolveJidToE164, l as isSelfChatMode, m as toWhatsappJidWithLid, n as normalizeE164, p as toWhatsappJid, r as resolveUserPath, u as jidToE164 } from "./text-runtime-BBSmIBHN.js";
9
- import { n as WHATSAPP_LEGACY_OUTBOUND_SEND_DEP_KEYS, t as whatsappPlugin } from "./channel-CNA0E9wp.js";
8
+ import { c as assertWebChannel, d as markdownToWhatsApp, h as toWhatsappJidWithLid, l as isSelfChatMode, m as toWhatsappJid, n as normalizeE164, p as resolveJidToE164, r as resolveUserPath, u as jidToE164 } from "./text-runtime-CpiloI73.js";
9
+ import { n as WHATSAPP_LEGACY_OUTBOUND_SEND_DEP_KEYS, t as whatsappPlugin } from "./channel-C9zebxrw.js";
10
10
  import { t as whatsappCommandPolicy } from "./command-policy-BIOSHySD.js";
11
- import { a as resolveWhatsAppGroupRequireMention, o as resolveWhatsAppGroupToolPolicy, s as resolveWhatsAppGroupIntroHint } from "./setup-core-DVEkfMVh.js";
11
+ import { a as resolveWhatsAppGroupRequireMention, o as resolveWhatsAppGroupToolPolicy, s as resolveWhatsAppGroupIntroHint } from "./setup-core-D0JxJ53T.js";
12
12
  import "./config-schema-CROZuhT-.js";
13
- import { t as whatsappSetupPlugin } from "./channel.setup-BfcLCLNn.js";
13
+ import { t as whatsappSetupPlugin } from "./channel.setup-BTi6IdDT.js";
14
14
  import { t as DEFAULT_WEB_MEDIA_BYTES } from "./constants-HU41RHGI.js";
15
15
  import { n as listWhatsAppDirectoryGroupsFromConfig, r as listWhatsAppDirectoryPeersFromConfig } from "./directory-config-Dijefxc3.js";
16
- import { n as testing } from "./access-control-BnFVCHHH.js";
17
- import { _ as extractLocationData, b as extractText, d as normalizeMessageContent, f as resolveInboundMediaMimetype, h as extractContextInfo, p as describeReplyContext, t as createWebSendApi } from "./send-api-89SE5WKV.js";
18
- import { r as waitForWaConnection, t as createWaSocket } from "./session-BW8RcCcb.js";
16
+ import { n as testing } from "./access-control-_oQx0_UZ.js";
17
+ import { _ as extractLocationData, b as extractText, d as normalizeMessageContent, f as resolveInboundMediaMimetype, h as extractContextInfo, p as describeReplyContext, t as createWebSendApi } from "./send-api-11yoHJhM.js";
18
+ import { r as waitForWaConnection, t as createWaSocket } from "./session-DlHpYSAl.js";
19
19
  import "openclaw/plugin-sdk/channel-actions";
20
20
  import "openclaw/plugin-sdk/account-resolution";
21
21
  import "openclaw/plugin-sdk/core";
@@ -1,5 +1,5 @@
1
1
  import { s as normalizeWhatsAppMessagingTarget } from "./normalize-target-bVWjgftN.js";
2
- import { f as registerWhatsAppApprovalReactionTarget, i as sendTypingWhatsApp, p as unregisterWhatsAppApprovalReactionTarget, t as sendMessageWhatsApp } from "./send-A9EqsNyz.js";
2
+ import { f as registerWhatsAppApprovalReactionTarget, i as sendTypingWhatsApp, p as unregisterWhatsAppApprovalReactionTarget, t as sendMessageWhatsApp } from "./send-BplHdEjw.js";
3
3
  import "./normalize-Bxwqo-bW.js";
4
4
  import { n as getWhatsAppRuntime } from "./runtime-BfAdAEYT.js";
5
5
  import { createSubsystemLogger } from "openclaw/plugin-sdk/runtime-env";
@@ -1,7 +1,7 @@
1
1
  import { t as __exportAll } from "./rolldown-runtime-D7D4PA-g.js";
2
2
  import { a as readWebCredsJsonRawSync, c as statWebCredsFileSync, i as readWebCredsJsonRaw, o as resolveWebCredsBackupPath, s as resolveWebCredsPath, t as assertWebCredsPathRegularFileOrMissing } from "./creds-files-B1kSWtBg.js";
3
- import { r as resolveUserPath } from "./text-runtime-BBSmIBHN.js";
4
- import { c as resolveComparableIdentity } from "./identity-Cm6bKAtk.js";
3
+ import { r as resolveUserPath } from "./text-runtime-CpiloI73.js";
4
+ import { c as resolveComparableIdentity } from "./identity-DdeafYji.js";
5
5
  import path from "node:path";
6
6
  import { resolveOAuthDir as resolveOAuthDir$1 } from "openclaw/plugin-sdk/state-paths";
7
7
  import { replaceFileAtomic } from "openclaw/plugin-sdk/security-runtime";
@@ -2,15 +2,15 @@ import { r as resolveDefaultWhatsAppAccountId, t as listAccountIds } from "./acc
2
2
  import { a as resolveWhatsAppAccount } from "./accounts-DgViSyJx.js";
3
3
  import { c as normalizeWhatsAppTarget, i as looksLikeWhatsAppTargetId, n as isWhatsAppNewsletterJid, o as normalizeWhatsAppAllowFromEntry, s as normalizeWhatsAppMessagingTarget, t as isWhatsAppGroupJid } from "./normalize-target-bVWjgftN.js";
4
4
  import { t as resolveWhatsAppOutboundTarget } from "./resolve-outbound-target-CcdugbDf.js";
5
- import { a as normalizeWhatsAppOutboundPayload, g as resolveWhatsAppReactionLevel, h as whatsappApprovalAuth, i as sendTypingWhatsApp, m as getWhatsAppApprovalApprovers, n as sendPollWhatsApp, o as normalizeWhatsAppPayloadText, s as normalizeWhatsAppPayloadTextPreservingIndentation, t as sendMessageWhatsApp } from "./send-A9EqsNyz.js";
5
+ import { a as normalizeWhatsAppOutboundPayload, g as resolveWhatsAppReactionLevel, h as whatsappApprovalAuth, i as sendTypingWhatsApp, m as getWhatsAppApprovalApprovers, n as sendPollWhatsApp, o as normalizeWhatsAppPayloadText, s as normalizeWhatsAppPayloadTextPreservingIndentation, t as sendMessageWhatsApp } from "./send-BplHdEjw.js";
6
6
  import "./normalize-Bxwqo-bW.js";
7
7
  import { n as getWhatsAppRuntime } from "./runtime-BfAdAEYT.js";
8
- import { p as toWhatsappJid } from "./text-runtime-BBSmIBHN.js";
8
+ import { m as toWhatsappJid } from "./text-runtime-CpiloI73.js";
9
9
  import { t as createWhatsAppLoginTool } from "./agent-tools-login-BX7eHgDm.js";
10
- import { i as lookupInboundMessageMetaForTarget } from "./quoted-message-DVOfpEja.js";
10
+ import { i as lookupInboundMessageMetaForTarget } from "./quoted-message-DqmWlbN7.js";
11
11
  import { t as whatsappCommandPolicy } from "./command-policy-BIOSHySD.js";
12
- import { a as resolveWhatsAppGroupRequireMention, c as resolveWhatsAppMentionStripRegexes, i as whatsappSetupWizardProxy, l as formatWhatsAppConfigAllowFromEntries, n as createWhatsAppPluginBase, o as resolveWhatsAppGroupToolPolicy, r as loadWhatsAppChannelRuntime, s as resolveWhatsAppGroupIntroHint, t as whatsappSetupAdapter } from "./setup-core-DVEkfMVh.js";
13
- import { f as readWebAuthExistsForDecision, n as WHATSAPP_AUTH_UNSTABLE_CODE } from "./auth-store-RyuCPHE0.js";
12
+ import { a as resolveWhatsAppGroupRequireMention, c as resolveWhatsAppMentionStripRegexes, i as whatsappSetupWizardProxy, l as formatWhatsAppConfigAllowFromEntries, n as createWhatsAppPluginBase, o as resolveWhatsAppGroupToolPolicy, r as loadWhatsAppChannelRuntime, s as resolveWhatsAppGroupIntroHint, t as whatsappSetupAdapter } from "./setup-core-D0JxJ53T.js";
13
+ import { f as readWebAuthExistsForDecision, n as WHATSAPP_AUTH_UNSTABLE_CODE } from "./auth-store-BRv2o3w2.js";
14
14
  import { t as detectWhatsAppLegacyStateMigrations } from "./state-migrations-D_BmQUR9.js";
15
15
  import { createActionGate as createActionGate$1 } from "openclaw/plugin-sdk/channel-actions";
16
16
  import { DEFAULT_ACCOUNT_ID, listCombinedAccountIds, normalizeOptionalAccountId, resolveListedDefaultAccountId } from "openclaw/plugin-sdk/account-core";
@@ -205,7 +205,7 @@ const whatsappApprovalCapability = createChannelApprovalCapability({
205
205
  accountId,
206
206
  request
207
207
  }),
208
- load: async () => (await import("./approval-handler.runtime-DLjPf_Mx.js")).whatsappApprovalNativeRuntime
208
+ load: async () => (await import("./approval-handler.runtime-DNBh4thG.js")).whatsappApprovalNativeRuntime
209
209
  })
210
210
  });
211
211
  //#endregion
@@ -302,13 +302,12 @@ function createWhatsAppOutboundBase({ chunker, sendMessageWhatsApp, sendPollWhat
302
302
  sendText: async ({ cfg, to, text, accountId, deps, gifPlayback, replyToId }) => {
303
303
  const normalizedText = normalizeText(text);
304
304
  if (skipEmptyText && !normalizedText) return { messageId: "" };
305
- const send = resolveOutboundSendDep(deps, "whatsapp", { legacyKeys: WHATSAPP_LEGACY_OUTBOUND_SEND_DEP_KEYS }) ?? sendMessageWhatsApp;
306
305
  const quotedMessageKey = resolveQuotedMessageKey({
307
306
  accountId: resolveQuoteLookupAccountId(cfg, accountId),
308
307
  to,
309
308
  replyToId
310
309
  });
311
- return await send(to, normalizedText, {
310
+ return await (quotedMessageKey ? sendMessageWhatsApp : resolveOutboundSendDep(deps, "whatsapp", { legacyKeys: WHATSAPP_LEGACY_OUTBOUND_SEND_DEP_KEYS }) ?? sendMessageWhatsApp)(to, normalizedText, {
312
311
  verbose: false,
313
312
  cfg,
314
313
  accountId: accountId ?? void 0,
@@ -317,13 +316,12 @@ function createWhatsAppOutboundBase({ chunker, sendMessageWhatsApp, sendPollWhat
317
316
  });
318
317
  },
319
318
  sendMedia: async ({ cfg, to, text, mediaUrl, mediaAccess, mediaLocalRoots, mediaReadFile, audioAsVoice, accountId, deps, gifPlayback, forceDocument, replyToId }) => {
320
- const send = resolveOutboundSendDep(deps, "whatsapp", { legacyKeys: WHATSAPP_LEGACY_OUTBOUND_SEND_DEP_KEYS }) ?? sendMessageWhatsApp;
321
319
  const quotedMessageKey = resolveQuotedMessageKey({
322
320
  accountId: resolveQuoteLookupAccountId(cfg, accountId),
323
321
  to,
324
322
  replyToId
325
323
  });
326
- return await send(to, normalizeText(text), {
324
+ return await (quotedMessageKey ? sendMessageWhatsApp : resolveOutboundSendDep(deps, "whatsapp", { legacyKeys: WHATSAPP_LEGACY_OUTBOUND_SEND_DEP_KEYS }) ?? sendMessageWhatsApp)(to, normalizeText(text), {
327
325
  verbose: false,
328
326
  cfg,
329
327
  mediaUrl,
@@ -603,7 +601,7 @@ function collectWhatsAppStatusIssues(accounts) {
603
601
  //#endregion
604
602
  //#region extensions/whatsapp/src/channel.ts
605
603
  const loadWhatsAppDirectoryConfig = createLazyRuntimeModule(() => import("./directory-config-Dijefxc3.js").then((n) => n.t));
606
- const loadWhatsAppChannelReactAction = createLazyRuntimeModule(() => import("./channel-react-action-CdYJKJWb.js"));
604
+ const loadWhatsAppChannelReactAction = createLazyRuntimeModule(() => import("./channel-react-action-C56UzM_r.js"));
607
605
  function resolveWhatsAppTargetInfo(raw) {
608
606
  const normalized = normalizeWhatsAppTarget(raw);
609
607
  if (!normalized) return null;
@@ -1,2 +1,2 @@
1
- import { t as whatsappPlugin } from "./channel-CNA0E9wp.js";
1
+ import { t as whatsappPlugin } from "./channel-C9zebxrw.js";
2
2
  export { whatsappPlugin };
@@ -1,7 +1,7 @@
1
1
  import { a as resolveWhatsAppAccount, s as resolveWhatsAppMediaMaxBytes } from "./accounts-DgViSyJx.js";
2
2
  import { c as normalizeWhatsAppTarget, t as isWhatsAppGroupJid } from "./normalize-target-bVWjgftN.js";
3
- import { r as resolveAuthorizedWhatsAppOutboundTarget, t as handleWhatsAppAction } from "./action-runtime-ClQLHIwf.js";
4
- import { t as sendMessageWhatsApp } from "./send-A9EqsNyz.js";
3
+ import { r as resolveAuthorizedWhatsAppOutboundTarget, t as handleWhatsAppAction } from "./action-runtime-D-FTwc8j.js";
4
+ import { t as sendMessageWhatsApp } from "./send-BplHdEjw.js";
5
5
  import "./normalize-Bxwqo-bW.js";
6
6
  import { jsonResult, readStringOrNumberParam, readStringParam as readStringParam$1, resolveReactionMessageId } from "openclaw/plugin-sdk/channel-actions";
7
7
  //#region extensions/whatsapp/src/channel-react-action.ts
@@ -1,9 +1,9 @@
1
1
  import { startWebLoginWithQr as startWebLoginWithQr$1, waitForWebLogin as waitForWebLogin$1 } from "./login-qr-runtime.js";
2
- import { c as logoutWeb$1, d as readWebAuthExistsBestEffort$1, f as readWebAuthExistsForDecision$1, g as readWebSelfId$1, h as readWebAuthState$1, m as readWebAuthSnapshotBestEffort$1, o as getWebAuthAgeMs$1, p as readWebAuthSnapshot$1, s as logWebSelfId$1, x as webAuthExists$1 } from "./auth-store-RyuCPHE0.js";
2
+ import { c as logoutWeb$1, d as readWebAuthExistsBestEffort$1, f as readWebAuthExistsForDecision$1, g as readWebSelfId$1, h as readWebAuthState$1, m as readWebAuthSnapshotBestEffort$1, o as getWebAuthAgeMs$1, p as readWebAuthSnapshot$1, s as logWebSelfId$1, x as webAuthExists$1 } from "./auth-store-BRv2o3w2.js";
3
3
  import { t as getActiveWebListener$1 } from "./active-listener-CFwkn3ho.js";
4
- import { t as monitorWebChannel$1 } from "./monitor-C5_QBO1-.js";
5
- import { t as loginWeb$1 } from "./login-B503Fwb8.js";
6
- import { whatsappSetupWizard as whatsappSetupWizard$1 } from "./setup-surface-ByAUWXyq.js";
4
+ import { t as monitorWebChannel$1 } from "./monitor-BVD90YEd.js";
5
+ import { t as loginWeb$1 } from "./login-FpqysWi0.js";
6
+ import { whatsappSetupWizard as whatsappSetupWizard$1 } from "./setup-surface-BpdIDwDg.js";
7
7
  //#region extensions/whatsapp/src/channel.runtime.ts
8
8
  function getActiveWebListener(...args) {
9
9
  return getActiveWebListener$1(...args);
@@ -1,8 +1,8 @@
1
- import { a as resolveWhatsAppGroupRequireMention, i as whatsappSetupWizardProxy, n as createWhatsAppPluginBase, o as resolveWhatsAppGroupToolPolicy, s as resolveWhatsAppGroupIntroHint, t as whatsappSetupAdapter } from "./setup-core-DVEkfMVh.js";
1
+ import { a as resolveWhatsAppGroupRequireMention, i as whatsappSetupWizardProxy, n as createWhatsAppPluginBase, o as resolveWhatsAppGroupToolPolicy, s as resolveWhatsAppGroupIntroHint, t as whatsappSetupAdapter } from "./setup-core-D0JxJ53T.js";
2
2
  import { t as detectWhatsAppLegacyStateMigrations } from "./state-migrations-D_BmQUR9.js";
3
3
  //#region extensions/whatsapp/src/channel.setup.ts
4
4
  async function isWhatsAppAuthConfigured(account) {
5
- const { readWebAuthState } = await import("./auth-store-RyuCPHE0.js").then((n) => n.i);
5
+ const { readWebAuthState } = await import("./auth-store-BRv2o3w2.js").then((n) => n.i);
6
6
  return await readWebAuthState(account.authDir) === "linked";
7
7
  }
8
8
  const whatsappSetupPlugin = {
@@ -1,8 +1,8 @@
1
1
  import { a as unregisterWhatsAppConnectionController, i as registerWhatsAppConnectionController, n as getStatusCode, t as formatError } from "./session-errors-CbsoQqoy.js";
2
2
  import { t as DEFAULT_WHATSAPP_SOCKET_TIMING } from "./socket-timing-DvMNkIge.js";
3
- import { c as logoutWeb, f as readWebAuthExistsForDecision, r as WhatsAppAuthUnstableError } from "./auth-store-RyuCPHE0.js";
4
- import { c as resolveComparableIdentity } from "./identity-Cm6bKAtk.js";
5
- import { r as waitForWaConnection, t as createWaSocket } from "./session-BW8RcCcb.js";
3
+ import { c as logoutWeb, f as readWebAuthExistsForDecision, r as WhatsAppAuthUnstableError } from "./auth-store-BRv2o3w2.js";
4
+ import { c as resolveComparableIdentity } from "./identity-DdeafYji.js";
5
+ import { r as waitForWaConnection, t as createWaSocket } from "./session-DlHpYSAl.js";
6
6
  import { computeBackoff, info, sleepWithAbort } from "openclaw/plugin-sdk/runtime-env";
7
7
  import { clamp } from "openclaw/plugin-sdk/text-utility-runtime";
8
8
  import { randomUUID } from "node:crypto";
@@ -208,7 +208,7 @@ var WhatsAppConnectionController = class {
208
208
  this.heartbeatSeconds = params.heartbeatSeconds;
209
209
  this.transportTimeoutMs = params.transportTimeoutMs;
210
210
  this.messageTimeoutMs = params.messageTimeoutMs;
211
- this.appSilenceTimeoutMs = Math.max(params.messageTimeoutMs, params.messageTimeoutMs * 4);
211
+ this.appSilenceTimeoutMs = params.messageTimeoutMs * 4;
212
212
  this.watchdogCheckMs = params.watchdogCheckMs;
213
213
  this.reconnectPolicy = params.reconnectPolicy;
214
214
  this.abortSignal = params.abortSignal;
@@ -298,7 +298,9 @@ var WhatsAppConnectionController = class {
298
298
  try {
299
299
  sock = await createWaSocket(false, this.verbose, {
300
300
  authDir: this.authDir,
301
- ...this.socketTiming
301
+ ...this.socketTiming,
302
+ ...params.getMessage ? { getMessage: params.getMessage } : {},
303
+ ...params.cachedGroupMetadata ? { cachedGroupMetadata: params.cachedGroupMetadata } : {}
302
304
  });
303
305
  await waitForWaConnection(sock, { timeoutMs: this.socketTiming.connectTimeoutMs });
304
306
  this.socketRef.current = sock;
@@ -2,7 +2,7 @@ import { c as normalizeWhatsAppTarget$1, t as isWhatsAppGroupJid$1 } from "./nor
2
2
  import { t as whatsappCommandPolicy$1 } from "./command-policy-BIOSHySD.js";
3
3
  import { t as resolveLegacyGroupSessionKey$1 } from "./group-session-contract-DDnZSsJ1.js";
4
4
  import { r as isLegacyGroupSessionKey$1, t as canonicalizeLegacySessionKey$1 } from "./session-contract-DMTm6Q_L.js";
5
- import { a as resolveWhatsAppRuntimeGroupPolicy$1, n as testing } from "./access-control-BnFVCHHH.js";
5
+ import { a as resolveWhatsAppRuntimeGroupPolicy$1, n as testing } from "./access-control-_oQx0_UZ.js";
6
6
  //#region extensions/whatsapp/contract-api.ts
7
7
  const canonicalizeLegacySessionKey = canonicalizeLegacySessionKey$1;
8
8
  const isLegacyGroupSessionKey = isLegacyGroupSessionKey$1;
@@ -1,4 +1,4 @@
1
- import { n as normalizeE164, u as jidToE164 } from "./text-runtime-BBSmIBHN.js";
1
+ import { n as normalizeE164, u as jidToE164 } from "./text-runtime-CpiloI73.js";
2
2
  //#region extensions/whatsapp/src/identity.ts
3
3
  const WHATSAPP_LID_RE = /@(lid|hosted\.lid)$/i;
4
4
  function normalizeDeviceScopedJid(jid) {
@@ -1,5 +1,5 @@
1
1
  import { n as getStatusCode, t as formatError } from "./session-errors-CbsoQqoy.js";
2
2
  import { t as createWhatsAppLoginTool } from "./agent-tools-login-BX7eHgDm.js";
3
- import { c as logoutWeb, g as readWebSelfId, l as pickWebChannel, o as getWebAuthAgeMs, s as logWebSelfId, t as WA_WEB_AUTH_DIR, x as webAuthExists, y as resolveDefaultWebAuthDir } from "./auth-store-RyuCPHE0.js";
3
+ import { c as logoutWeb, g as readWebSelfId, l as pickWebChannel, o as getWebAuthAgeMs, s as logWebSelfId, t as WA_WEB_AUTH_DIR, x as webAuthExists, y as resolveDefaultWebAuthDir } from "./auth-store-BRv2o3w2.js";
4
4
  import { t as getActiveWebListener } from "./active-listener-CFwkn3ho.js";
5
5
  export { WA_WEB_AUTH_DIR, createWhatsAppLoginTool, formatError, getActiveWebListener, getStatusCode, getWebAuthAgeMs, logWebSelfId, logoutWeb, pickWebChannel, readWebSelfId, resolveDefaultWebAuthDir, webAuthExists };
@@ -1,9 +1,9 @@
1
1
  import { t as __exportAll } from "./rolldown-runtime-D7D4PA-g.js";
2
2
  import { a as resolveWhatsAppAccount } from "./accounts-DgViSyJx.js";
3
3
  import { a as resolveWhatsAppSocketTiming } from "./socket-timing-DvMNkIge.js";
4
- import { b as restoreCredsFromBackupIfNeeded } from "./auth-store-RyuCPHE0.js";
5
- import { i as renderQrTerminal, t as createWaSocket } from "./session-BW8RcCcb.js";
6
- import { a as closeWaSocketSoon, o as waitForWhatsAppLoginResult } from "./connection-controller-BDuM0Kc7.js";
4
+ import { b as restoreCredsFromBackupIfNeeded } from "./auth-store-BRv2o3w2.js";
5
+ import { i as renderQrTerminal, t as createWaSocket } from "./session-DlHpYSAl.js";
6
+ import { a as closeWaSocketSoon, o as waitForWhatsAppLoginResult } from "./connection-controller-Ds4puj_n.js";
7
7
  import { formatCliCommand } from "openclaw/plugin-sdk/cli-runtime";
8
8
  import { logInfo } from "openclaw/plugin-sdk/logging-core";
9
9
  import { danger, defaultRuntime, success } from "openclaw/plugin-sdk/runtime-env";
@@ -1,10 +1,10 @@
1
1
  import { a as resolveWhatsAppAccount } from "./accounts-DgViSyJx.js";
2
2
  import { t as formatError } from "./session-errors-CbsoQqoy.js";
3
3
  import { a as resolveWhatsAppSocketTiming } from "./socket-timing-DvMNkIge.js";
4
- import { c as logoutWeb, f as readWebAuthExistsForDecision, g as readWebSelfId, n as WHATSAPP_AUTH_UNSTABLE_CODE } from "./auth-store-RyuCPHE0.js";
5
- import { t as createWaSocket } from "./session-BW8RcCcb.js";
4
+ import { c as logoutWeb, f as readWebAuthExistsForDecision, g as readWebSelfId, n as WHATSAPP_AUTH_UNSTABLE_CODE } from "./auth-store-BRv2o3w2.js";
5
+ import { t as createWaSocket } from "./session-DlHpYSAl.js";
6
6
  import { t as getActiveWebListener } from "./active-listener-CFwkn3ho.js";
7
- import { i as closeWaSocket, o as waitForWhatsAppLoginResult, t as WHATSAPP_LOGGED_OUT_QR_MESSAGE } from "./connection-controller-BDuM0Kc7.js";
7
+ import { i as closeWaSocket, o as waitForWhatsAppLoginResult, t as WHATSAPP_LOGGED_OUT_QR_MESSAGE } from "./connection-controller-Ds4puj_n.js";
8
8
  import { logInfo } from "openclaw/plugin-sdk/logging-core";
9
9
  import { danger, defaultRuntime, info, success } from "openclaw/plugin-sdk/runtime-env";
10
10
  import { renderQrPngDataUrl } from "openclaw/plugin-sdk/media-runtime";
@@ -1,7 +1,7 @@
1
1
  //#region extensions/whatsapp/login-qr-runtime.ts
2
2
  let loginQrModulePromise = null;
3
3
  function loadLoginQrModule() {
4
- loginQrModulePromise ??= import("./login-qr-AgwdQyj_.js");
4
+ loginQrModulePromise ??= import("./login-qr-BjfpyyN0.js");
5
5
  return loginQrModulePromise;
6
6
  }
7
7
  async function startWebLoginWithQr(...args) {
@@ -1,18 +1,18 @@
1
1
  import { a as resolveWhatsAppAccount, s as resolveWhatsAppMediaMaxBytes } from "./accounts-DgViSyJx.js";
2
- import { a as normalizeWhatsAppOutboundPayload, c as prepareWhatsAppOutboundMedia, d as maybeResolveWhatsAppApprovalReaction, g as resolveWhatsAppReactionLevel, l as sendWhatsAppOutboundWithRetry, r as sendReactionWhatsApp, s as normalizeWhatsAppPayloadTextPreservingIndentation } from "./send-A9EqsNyz.js";
2
+ import { a as normalizeWhatsAppOutboundPayload, c as prepareWhatsAppOutboundMedia, d as maybeResolveWhatsAppApprovalReaction, g as resolveWhatsAppReactionLevel, l as sendWhatsAppOutboundWithRetry, r as sendReactionWhatsApp, s as normalizeWhatsAppPayloadTextPreservingIndentation } from "./send-BplHdEjw.js";
3
3
  import { n as getWhatsAppRuntime } from "./runtime-BfAdAEYT.js";
4
4
  import { n as getStatusCode, r as getRegisteredWhatsAppConnectionController, t as formatError } from "./session-errors-CbsoQqoy.js";
5
5
  import { a as resolveWhatsAppSocketTiming, i as resolveWhatsAppSocketOperationTimeoutMs, n as createWhatsAppSocketOperationTimeoutAdapter, o as withWhatsAppSocketOperationTimeout, r as isWhatsAppSocketOperationTimeoutError } from "./socket-timing-DvMNkIge.js";
6
- import { d as markdownToWhatsApp, f as resolveJidToE164, l as isSelfChatMode, n as normalizeE164, t as convertMarkdownTables$1, u as jidToE164 } from "./text-runtime-BBSmIBHN.js";
7
- import { n as cacheInboundMessageMeta, r as lookupInboundMessageMeta, t as buildQuotedMessageOptions } from "./quoted-message-DVOfpEja.js";
8
- import { g as readWebSelfId, o as getWebAuthAgeMs, r as WhatsAppAuthUnstableError, v as readWebSelfIdentityForDecision } from "./auth-store-RyuCPHE0.js";
9
- import { a as getSelfIdentity, c as resolveComparableIdentity, i as getReplyContext, n as getMentionIdentities, o as getSenderIdentity, r as getPrimaryIdentityId, s as identitiesOverlap, t as getComparableIdentityValues } from "./identity-Cm6bKAtk.js";
6
+ import { d as markdownToWhatsApp, f as resolveEquivalentWhatsAppDirectChatJids, l as isSelfChatMode, n as normalizeE164, p as resolveJidToE164, t as convertMarkdownTables$1, u as jidToE164 } from "./text-runtime-CpiloI73.js";
7
+ import { n as cacheInboundMessageMeta, r as lookupInboundMessageMeta, t as buildQuotedMessageOptions } from "./quoted-message-DqmWlbN7.js";
8
+ import { g as readWebSelfId, o as getWebAuthAgeMs, r as WhatsAppAuthUnstableError, v as readWebSelfIdentityForDecision } from "./auth-store-BRv2o3w2.js";
9
+ import { a as getSelfIdentity, c as resolveComparableIdentity, i as getReplyContext, n as getMentionIdentities, o as getSenderIdentity, r as getPrimaryIdentityId, s as identitiesOverlap, t as getComparableIdentityValues } from "./identity-DdeafYji.js";
10
10
  import { n as resolveWhatsAppGroupsConfigPath } from "./group-config-path-BGyzT9Lg.js";
11
- import { c as requireWhatsAppInboundAdmission, i as resolveWhatsAppInboundPolicy, l as resolveWhatsAppGroupConversationId, o as buildDeprecatedFlatWhatsAppInboundAdmission, r as resolveWhatsAppCommandAuthorized, s as requireAdmittedWhatsAppInboundMessage, t as checkInboundAccessControl } from "./access-control-BnFVCHHH.js";
12
- import { _ as extractLocationData, a as mayContainWhatsAppOutboundMention, b as extractText, c as DisconnectReason, d as normalizeMessageContent, f as resolveInboundMediaMimetype, g as extractExternalAdReplyContext, h as extractContextInfo, i as addWhatsAppOutboundMentionsToContent, l as downloadMediaMessage, m as extractContactContext, n as listWhatsAppSendResultMessageIds, o as resolveWhatsAppOutboundMentions, p as describeReplyContext, r as normalizeWhatsAppSendResult, s as addWhatsAppImagePreviewFields, t as createWebSendApi, u as isJidGroup, v as extractMediaPlaceholder, x as hasInboundUserContent, y as extractMentionedJids } from "./send-api-89SE5WKV.js";
13
- import { r as waitForWaConnection, t as createWaSocket } from "./session-BW8RcCcb.js";
11
+ import { c as requireWhatsAppInboundAdmission, i as resolveWhatsAppInboundPolicy, l as resolveWhatsAppGroupConversationId, o as buildDeprecatedFlatWhatsAppInboundAdmission, r as resolveWhatsAppCommandAuthorized, s as requireAdmittedWhatsAppInboundMessage, t as checkInboundAccessControl } from "./access-control-_oQx0_UZ.js";
12
+ import { _ as extractLocationData, a as mayContainWhatsAppOutboundMention, b as extractText, c as DisconnectReason, d as normalizeMessageContent, f as resolveInboundMediaMimetype, g as extractExternalAdReplyContext, h as extractContextInfo, i as addWhatsAppOutboundMentionsToContent, l as downloadMediaMessage, m as extractContactContext, n as listWhatsAppSendResultMessageIds, o as resolveWhatsAppOutboundMentions, p as describeReplyContext, r as normalizeWhatsAppSendResult, s as addWhatsAppImagePreviewFields, t as createWebSendApi, u as isJidGroup, v as extractMediaPlaceholder, x as hasInboundUserContent, y as extractMentionedJids } from "./send-api-11yoHJhM.js";
13
+ import { r as waitForWaConnection, t as createWaSocket } from "./session-DlHpYSAl.js";
14
14
  import { t as BufferJSON } from "./session.runtime-CyooSQvj.js";
15
- import { c as computeBackoff, d as resolveReconnectPolicy, f as sleepWithAbort, l as newConnectionId, n as WHATSAPP_WATCHDOG_TIMEOUT_ERROR, r as WhatsAppConnectionController, s as DEFAULT_RECONNECT_POLICY, u as resolveHeartbeatSeconds } from "./connection-controller-BDuM0Kc7.js";
15
+ import { c as computeBackoff, d as resolveReconnectPolicy, f as sleepWithAbort, l as newConnectionId, n as WHATSAPP_WATCHDOG_TIMEOUT_ERROR, r as WhatsAppConnectionController, s as DEFAULT_RECONNECT_POLICY, u as resolveHeartbeatSeconds } from "./connection-controller-Ds4puj_n.js";
16
16
  import { resolveAccountEntry } from "openclaw/plugin-sdk/account-core";
17
17
  import { normalizeLowercaseStringOrEmpty, normalizeStringEntries, uniqueStrings } from "openclaw/plugin-sdk/string-coerce-runtime";
18
18
  import { createChannelMessageReplyPipeline, createDurableInboundReceiveJournalFromQueue, createMessageReceiptFromOutboundResults, deliverInboundReplyWithMessageSendContext, resolveChannelMessageSourceReplyDeliveryMode } from "openclaw/plugin-sdk/channel-outbound";
@@ -574,6 +574,7 @@ async function downloadQuotedInboundMedia(msg, sock, maxBytes = 50 * 1024 * 1024
574
574
  const LOGGED_OUT_STATUS = DisconnectReason?.loggedOut ?? 401;
575
575
  const RECONNECT_IN_PROGRESS_ERROR = "no active socket - reconnection in progress";
576
576
  const GROUP_META_TTL_MS = 300 * 1e3;
577
+ const BAILEYS_MESSAGE_TTL_MS = 600 * 1e3;
577
578
  const INBOUND_CLOSE_DRAIN_TIMEOUT_MS = 5e3;
578
579
  function resolveGroupMetadataExpiresAt(nowRaw = Date.now()) {
579
580
  const now = asDateTimestampMs(nowRaw);
@@ -611,6 +612,30 @@ function readGroupMetadataCacheEntry(cache, jid) {
611
612
  cache.set(jid, entry);
612
613
  return entry;
613
614
  }
615
+ function rememberWhatsAppBaileysCacheEntry(cache, key, value, ttlMs) {
616
+ if (!cache) return;
617
+ if (cache.has(key)) cache.delete(key);
618
+ cache.set(key, {
619
+ expiresAt: Date.now() + ttlMs,
620
+ value
621
+ });
622
+ while (cache.size > 500) {
623
+ const oldest = cache.keys().next();
624
+ if (oldest.done) break;
625
+ cache.delete(oldest.value);
626
+ }
627
+ }
628
+ function readWhatsAppBaileysCacheEntry(cache, key) {
629
+ const entry = cache.get(key);
630
+ if (!entry) return;
631
+ if (entry.expiresAt <= Date.now()) {
632
+ cache.delete(key);
633
+ return;
634
+ }
635
+ cache.delete(key);
636
+ cache.set(key, entry);
637
+ return entry.value;
638
+ }
614
639
  function logWhatsAppVerbose(enabled, message) {
615
640
  if (!enabled) return;
616
641
  defaultRuntime.log(message);
@@ -767,10 +792,21 @@ async function attachWebInboxToSocket(options) {
767
792
  const groupMetadataCache = options.groupMetadataCache ?? /* @__PURE__ */ new Map();
768
793
  const groupMetaCache = /* @__PURE__ */ new Map();
769
794
  const lidLookup = sock.signalRepository?.lidMapping;
795
+ const publishedGroupMetadataJids = /* @__PURE__ */ new Set();
796
+ const invalidatedGroupMetadataJids = /* @__PURE__ */ new Set();
797
+ let groupMetadataCacheClosed = false;
770
798
  const resolveInboundJid = async (jid) => resolveJidToE164(jid, {
771
799
  authDir: options.authDir,
772
800
  lidLookup
773
801
  });
802
+ const resolveReactionTargetJids = async (jid) => resolveEquivalentWhatsAppDirectChatJids(jid, {
803
+ authDir: options.authDir,
804
+ lidLookup
805
+ });
806
+ const rememberBaileysMessage = (remoteJid, messageId, message) => {
807
+ if (!options.recentMessageKeys || !remoteJid || !messageId || !message) return;
808
+ rememberWhatsAppBaileysCacheEntry(options.recentMessageKeys, `${remoteJid}:${messageId}`, message, BAILEYS_MESSAGE_TTL_MS);
809
+ };
774
810
  const rememberOutboundMessage = (remoteJid, result) => {
775
811
  const messageId = typeof result === "object" && result && "key" in result ? result.key?.id ?? "" : "";
776
812
  if (!messageId) return;
@@ -779,6 +815,7 @@ async function attachWebInboxToSocket(options) {
779
815
  remoteJid,
780
816
  messageId
781
817
  });
818
+ rememberBaileysMessage(remoteJid, messageId, typeof result === "object" && result && "message" in result ? result.message : void 0);
782
819
  };
783
820
  const trackLateAcceptedSend = (jid, promise) => {
784
821
  promise.then((result) => {
@@ -849,7 +886,10 @@ async function attachWebInboxToSocket(options) {
849
886
  const cached = readGroupMetadataCacheEntry(groupMetaCache, jid);
850
887
  if (cached) return cached;
851
888
  try {
852
- const entry = await summarizeGroupMeta(await (getCurrentSock() ?? sock).groupMetadata(jid));
889
+ const meta = await (getCurrentSock() ?? sock).groupMetadata(jid);
890
+ rememberWhatsAppBaileysCacheEntry(options.baileysGroupMetaCache, jid, meta, GROUP_META_TTL_MS);
891
+ publishedGroupMetadataJids.add(jid);
892
+ const entry = await summarizeGroupMeta(meta);
853
893
  rememberGroupMetadataCacheEntry(groupMetadataCache, jid, {
854
894
  subject: entry.subject,
855
895
  expires: entry.expires
@@ -1231,6 +1271,7 @@ async function attachWebInboxToSocket(options) {
1231
1271
  const handleMessagesUpsert = async (upsert) => {
1232
1272
  if (upsert.type !== "notify" && upsert.type !== "append") return;
1233
1273
  for (const msg of upsert.messages ?? []) {
1274
+ rememberBaileysMessage(msg.key?.remoteJid, msg.key?.id, msg.message);
1234
1275
  const receiveOrder = nextReceiveOrder++;
1235
1276
  if (await maybeResolveWhatsAppApprovalReaction({
1236
1277
  cfg: options.loadConfig?.() ?? options.cfg,
@@ -1239,6 +1280,7 @@ async function attachWebInboxToSocket(options) {
1239
1280
  selfJid: self.jid,
1240
1281
  selfLid: self.lid,
1241
1282
  resolveInboundJid,
1283
+ resolveReactionTargetJids,
1242
1284
  logVerboseMessage: (message) => logWhatsAppVerbose(options.verbose, message)
1243
1285
  })) continue;
1244
1286
  await processDurableInboundMessage(msg, upsert.type, receiveOrder);
@@ -1267,6 +1309,7 @@ async function attachWebInboxToSocket(options) {
1267
1309
  }
1268
1310
  };
1269
1311
  const drainInboundBeforeSocketClose = async () => {
1312
+ groupMetadataCacheClosed = true;
1270
1313
  await waitForPendingMessageHandlers();
1271
1314
  await drainDebouncedInboundMessages();
1272
1315
  };
@@ -1303,8 +1346,41 @@ async function attachWebInboxToSocket(options) {
1303
1346
  });
1304
1347
  }
1305
1348
  };
1306
- const detachMessagesUpsert = attachEmitterListener(sock.ev, "messages.upsert", handleMessagesUpsertEvent);
1307
- const detachConnectionUpdate = attachEmitterListener(sock.ev, "connection.update", handleConnectionUpdate);
1349
+ const attachSockListener = (event, listener) => attachEmitterListener(sock.ev, event, listener);
1350
+ const detachMessagesUpsert = attachSockListener("messages.upsert", handleMessagesUpsertEvent);
1351
+ const detachConnectionUpdate = attachSockListener("connection.update", handleConnectionUpdate);
1352
+ const isFullGroupMetadataUpdate = (update) => typeof update.id === "string" && typeof update.subject === "string" && Array.isArray(update.participants);
1353
+ const rememberFullGroupMetadataUpdate = (jid, meta) => {
1354
+ if (groupMetadataCacheClosed) return;
1355
+ rememberWhatsAppBaileysCacheEntry(options.baileysGroupMetaCache, jid, meta, GROUP_META_TTL_MS);
1356
+ publishedGroupMetadataJids.add(jid);
1357
+ invalidatedGroupMetadataJids.delete(jid);
1358
+ rememberGroupMetadataCacheEntry(groupMetadataCache, jid, summarizeGroupMetaForReconnectCache(meta));
1359
+ groupMetaCache.delete(jid);
1360
+ };
1361
+ const forgetFullGroupMetadata = (jid) => {
1362
+ options.baileysGroupMetaCache?.delete(jid);
1363
+ groupMetadataCache.delete(jid);
1364
+ groupMetaCache.delete(jid);
1365
+ publishedGroupMetadataJids.delete(jid);
1366
+ invalidatedGroupMetadataJids.add(jid);
1367
+ };
1368
+ const detachGroupsUpsert = attachSockListener("groups.upsert", ((groups) => {
1369
+ for (const group of groups) if (group.id) rememberFullGroupMetadataUpdate(group.id, group);
1370
+ }));
1371
+ const detachGroupsUpdate = attachSockListener("groups.update", ((updates) => {
1372
+ for (const update of updates) {
1373
+ if (!update.id) continue;
1374
+ if (isFullGroupMetadataUpdate(update)) {
1375
+ rememberFullGroupMetadataUpdate(update.id, update);
1376
+ continue;
1377
+ }
1378
+ forgetFullGroupMetadata(update.id);
1379
+ }
1380
+ }));
1381
+ const detachGroupParticipantsUpdate = attachSockListener("group-participants.update", ((update) => {
1382
+ forgetFullGroupMetadata(update.id);
1383
+ }));
1308
1384
  const replayTask = replayPendingDurableInboundMessages().catch((err) => {
1309
1385
  inboundLogger.error({ error: String(err) }, "failed replaying durable WhatsApp inbound");
1310
1386
  inboundConsoleLog.error(`Failed replaying durable WhatsApp inbound: ${String(err)}`);
@@ -1316,7 +1392,12 @@ async function attachWebInboxToSocket(options) {
1316
1392
  (async () => {
1317
1393
  try {
1318
1394
  const groups = await sock.groupFetchAllParticipating();
1319
- for (const [jid, meta] of Object.entries(groups ?? {})) if (meta) rememberGroupMetadataCacheEntry(groupMetadataCache, jid, summarizeGroupMetaForReconnectCache(meta));
1395
+ if (groupMetadataCacheClosed) return;
1396
+ for (const [jid, meta] of Object.entries(groups ?? {})) if (meta && !publishedGroupMetadataJids.has(jid) && !invalidatedGroupMetadataJids.has(jid)) {
1397
+ rememberGroupMetadataCacheEntry(groupMetadataCache, jid, summarizeGroupMetaForReconnectCache(meta));
1398
+ rememberWhatsAppBaileysCacheEntry(options.baileysGroupMetaCache, jid, meta, GROUP_META_TTL_MS);
1399
+ publishedGroupMetadataJids.add(jid);
1400
+ }
1320
1401
  logWhatsAppVerbose(options.verbose, `Hydrated ${Object.keys(groups ?? {}).length} participating groups on connect`);
1321
1402
  } catch (err) {
1322
1403
  const error = String(err);
@@ -1336,6 +1417,9 @@ async function attachWebInboxToSocket(options) {
1336
1417
  try {
1337
1418
  detachMessagesUpsert();
1338
1419
  detachConnectionUpdate();
1420
+ detachGroupsUpsert();
1421
+ detachGroupsUpdate();
1422
+ detachGroupParticipantsUpdate();
1339
1423
  await drainInboundBeforeSocketCloseWithTimeout();
1340
1424
  } catch (err) {
1341
1425
  logWhatsAppVerbose(options.verbose, `Inbound close drain failed: ${String(err)}`);
@@ -1362,9 +1446,16 @@ async function attachWebInboxToSocket(options) {
1362
1446
  }
1363
1447
  async function monitorWebInbox(options) {
1364
1448
  const socketTiming = options.socketTiming ?? resolveWhatsAppSocketTiming(options.cfg);
1449
+ const recentMessageKeys = options.recentMessageKeys ?? /* @__PURE__ */ new Map();
1450
+ const baileysGroupMetaCache = options.baileysGroupMetaCache ?? /* @__PURE__ */ new Map();
1365
1451
  const sock = await createWaSocket(false, options.verbose, {
1366
1452
  authDir: options.authDir,
1367
- ...socketTiming
1453
+ ...socketTiming,
1454
+ getMessage: async (key) => key.id && key.remoteJid ? readWhatsAppBaileysCacheEntry(recentMessageKeys, `${key.remoteJid}:${key.id}`) : void 0,
1455
+ cachedGroupMetadata: async (jid) => {
1456
+ const meta = readWhatsAppBaileysCacheEntry(baileysGroupMetaCache, jid);
1457
+ return meta?.participants?.length ? meta : void 0;
1458
+ }
1368
1459
  });
1369
1460
  try {
1370
1461
  await waitForWaConnection(sock, { timeoutMs: socketTiming.connectTimeoutMs });
@@ -1381,7 +1472,9 @@ async function monitorWebInbox(options) {
1381
1472
  },
1382
1473
  shouldDebounce: shouldDebounce ? (msg) => shouldDebounce(normalizeAdmittedWebInboundMessage(msg)) : void 0,
1383
1474
  socketTiming,
1384
- sock
1475
+ sock,
1476
+ recentMessageKeys,
1477
+ baileysGroupMetaCache
1385
1478
  });
1386
1479
  }
1387
1480
  //#endregion
@@ -2330,6 +2423,9 @@ function whatsAppReplyDeliveryVisibility(visibleReplySent) {
2330
2423
  function whatsAppReplyDeliveryVisibilityFromDurableResult(result) {
2331
2424
  return whatsAppReplyDeliveryVisibility(result.visibleReplySent === true);
2332
2425
  }
2426
+ function readTrimmedString(value) {
2427
+ return typeof value === "string" ? value.trim() : "";
2428
+ }
2333
2429
  function markWhatsAppReplyDeliveryErrorVisibleAfterFlush(error, flushResult) {
2334
2430
  return flushResult.delivered > 0 ? markWhatsAppVisibleDeliveryError(error) : error;
2335
2431
  }
@@ -2346,6 +2442,15 @@ function logWhatsAppReplyDeliveryError(params) {
2346
2442
  from: params.msg.platform.recipientJid ?? null
2347
2443
  }, "auto-reply delivery failed");
2348
2444
  }
2445
+ function resolveWhatsAppDurableReplyToId(params) {
2446
+ if (params.payload.replyToId === null) return null;
2447
+ const explicitPayloadReplyToId = readTrimmedString(params.payload.replyToId);
2448
+ if (explicitPayloadReplyToId) return explicitPayloadReplyToId;
2449
+ const hasVisibleInboundReplyTarget = Boolean(readTrimmedString(params.context.ReplyToId)) || Boolean(readTrimmedString(params.context.ReplyToIdFull));
2450
+ const currentInboundMessageId = readTrimmedString(params.msg.event.id);
2451
+ if (params.info.kind === "final" && hasVisibleInboundReplyTarget && currentInboundMessageId) return currentInboundMessageId;
2452
+ return null;
2453
+ }
2349
2454
  function resolveWhatsAppDisableBlockStreaming(cfg) {
2350
2455
  if (typeof cfg.channels?.whatsapp?.blockStreaming !== "boolean") return;
2351
2456
  return !cfg.channels.whatsapp.blockStreaming;
@@ -2662,6 +2767,12 @@ async function dispatchWhatsAppBufferedReply(params) {
2662
2767
  payload: normalizedDeliveryPayload,
2663
2768
  info,
2664
2769
  to: conversationId,
2770
+ replyToId: resolveWhatsAppDurableReplyToId({
2771
+ context: params.context,
2772
+ info,
2773
+ msg: params.msg,
2774
+ payload: normalizedDeliveryPayload
2775
+ }),
2665
2776
  formatting: {
2666
2777
  textLimit,
2667
2778
  tableMode,
@@ -3643,6 +3754,8 @@ async function monitorWebChannel(verbose, listenerFactory = attachWebInboxToSock
3643
3754
  const groupHistories = /* @__PURE__ */ new Map();
3644
3755
  const groupMemberNames = /* @__PURE__ */ new Map();
3645
3756
  const groupMetadataCache = /* @__PURE__ */ new Map();
3757
+ const recentMessageKeys = /* @__PURE__ */ new Map();
3758
+ const baileysGroupMetaCache = /* @__PURE__ */ new Map();
3646
3759
  const echoTracker = createEchoTracker({
3647
3760
  maxItems: 100,
3648
3761
  logVerbose
@@ -3700,6 +3813,11 @@ async function monitorWebChannel(verbose, listenerFactory = attachWebInboxToSock
3700
3813
  try {
3701
3814
  connection = await controller.openConnection({
3702
3815
  connectionId,
3816
+ getMessage: async (key) => key.id && key.remoteJid ? readWhatsAppBaileysCacheEntry(recentMessageKeys, `${key.remoteJid}:${key.id}`) : void 0,
3817
+ cachedGroupMetadata: async (jid) => {
3818
+ const meta = readWhatsAppBaileysCacheEntry(baileysGroupMetaCache, jid);
3819
+ return meta?.participants?.length ? meta : void 0;
3820
+ },
3703
3821
  createListener: async ({ sock, connection: connectionLocal }) => {
3704
3822
  const onMessage = createWebOnMessageHandler({
3705
3823
  cfg,
@@ -3734,6 +3852,8 @@ async function monitorWebChannel(verbose, listenerFactory = attachWebInboxToSock
3734
3852
  disconnectRetryPolicy: reconnectPolicy,
3735
3853
  disconnectRetryAbortSignal: controller.getDisconnectRetryAbortSignal(),
3736
3854
  groupMetadataCache,
3855
+ recentMessageKeys,
3856
+ baileysGroupMetaCache,
3737
3857
  onMessage: async (msg) => {
3738
3858
  const normalized = normalizeWebInboundMessage(msg);
3739
3859
  const inboundAt = Date.now();
@@ -1,4 +1,4 @@
1
- import { u as jidToE164 } from "./text-runtime-BBSmIBHN.js";
1
+ import { u as jidToE164 } from "./text-runtime-CpiloI73.js";
2
2
  //#region extensions/whatsapp/src/quoted-message.ts
3
3
  const CACHE_TTL_MS = 600 * 1e3;
4
4
  const MAX_ENTRIES = 500;
@@ -1,16 +1,16 @@
1
1
  import { o as resolveWebCredsBackupPath, r as hasWebCredsSync, s as resolveWebCredsPath } from "./creds-files-B1kSWtBg.js";
2
- import { n as whatsAppActionRuntime, t as handleWhatsAppAction } from "./action-runtime-ClQLHIwf.js";
3
- import { i as sendTypingWhatsApp, n as sendPollWhatsApp, r as sendReactionWhatsApp, t as sendMessageWhatsApp } from "./send-A9EqsNyz.js";
2
+ import { n as whatsAppActionRuntime, t as handleWhatsAppAction } from "./action-runtime-D-FTwc8j.js";
3
+ import { i as sendTypingWhatsApp, n as sendPollWhatsApp, r as sendReactionWhatsApp, t as sendMessageWhatsApp } from "./send-BplHdEjw.js";
4
4
  import { r as setWhatsAppRuntime } from "./runtime-BfAdAEYT.js";
5
5
  import { n as getStatusCode, t as formatError } from "./session-errors-CbsoQqoy.js";
6
6
  import { startWebLoginWithQr, waitForWebLogin } from "./login-qr-runtime.js";
7
7
  import { t as createWhatsAppLoginTool } from "./agent-tools-login-BX7eHgDm.js";
8
- import { C as waitForCredsSaveQueue, T as writeCredsJsonAtomically, _ as readWebSelfIdentity, a as formatWhatsAppWebAuthStatusState, b as restoreCredsFromBackupIfNeeded, c as logoutWeb, d as readWebAuthExistsBestEffort, f as readWebAuthExistsForDecision, g as readWebSelfId, h as readWebAuthState, l as pickWebChannel, m as readWebAuthSnapshotBestEffort, n as WHATSAPP_AUTH_UNSTABLE_CODE, o as getWebAuthAgeMs, p as readWebAuthSnapshot, r as WhatsAppAuthUnstableError, s as logWebSelfId, t as WA_WEB_AUTH_DIR, u as readCredsJsonRaw, v as readWebSelfIdentityForDecision, w as waitForCredsSaveQueueWithTimeout, x as webAuthExists, y as resolveDefaultWebAuthDir } from "./auth-store-RyuCPHE0.js";
8
+ import { C as waitForCredsSaveQueue, T as writeCredsJsonAtomically, _ as readWebSelfIdentity, a as formatWhatsAppWebAuthStatusState, b as restoreCredsFromBackupIfNeeded, c as logoutWeb, d as readWebAuthExistsBestEffort, f as readWebAuthExistsForDecision, g as readWebSelfId, h as readWebAuthState, l as pickWebChannel, m as readWebAuthSnapshotBestEffort, n as WHATSAPP_AUTH_UNSTABLE_CODE, o as getWebAuthAgeMs, p as readWebAuthSnapshot, r as WhatsAppAuthUnstableError, s as logWebSelfId, t as WA_WEB_AUTH_DIR, u as readCredsJsonRaw, v as readWebSelfIdentityForDecision, w as waitForCredsSaveQueueWithTimeout, x as webAuthExists, y as resolveDefaultWebAuthDir } from "./auth-store-BRv2o3w2.js";
9
9
  import { t as DEFAULT_WEB_MEDIA_BYTES } from "./constants-HU41RHGI.js";
10
- import { _ as extractLocationData, b as extractText, m as extractContactContext, v as extractMediaPlaceholder } from "./send-api-89SE5WKV.js";
11
- import { n as newConnectionId, r as waitForWaConnection, t as createWaSocket } from "./session-BW8RcCcb.js";
10
+ import { _ as extractLocationData, b as extractText, m as extractContactContext, v as extractMediaPlaceholder } from "./send-api-11yoHJhM.js";
11
+ import { n as newConnectionId, r as waitForWaConnection, t as createWaSocket } from "./session-DlHpYSAl.js";
12
12
  import { n as resolveWebAccountId, t as getActiveWebListener } from "./active-listener-CFwkn3ho.js";
13
- import { a as loadWebMediaRaw, c as monitorWebInbox, i as loadWebMedia, l as resetWebInboundDedupe, n as LocalMediaAccessError, o as optimizeImageToJpeg, r as getDefaultLocalRoots, s as optimizeImageToPng, t as monitorWebChannel } from "./monitor-C5_QBO1-.js";
14
- import { t as loginWeb } from "./login-B503Fwb8.js";
13
+ import { a as loadWebMediaRaw, c as monitorWebInbox, i as loadWebMedia, l as resetWebInboundDedupe, n as LocalMediaAccessError, o as optimizeImageToJpeg, r as getDefaultLocalRoots, s as optimizeImageToPng, t as monitorWebChannel } from "./monitor-BVD90YEd.js";
14
+ import { t as loginWeb } from "./login-FpqysWi0.js";
15
15
  import { HEARTBEAT_PROMPT, HEARTBEAT_TOKEN, SILENT_REPLY_TOKEN, stripHeartbeatToken } from "openclaw/plugin-sdk/reply-runtime";
16
16
  export { DEFAULT_WEB_MEDIA_BYTES, HEARTBEAT_PROMPT, HEARTBEAT_TOKEN, LocalMediaAccessError, SILENT_REPLY_TOKEN, WA_WEB_AUTH_DIR, WHATSAPP_AUTH_UNSTABLE_CODE, WhatsAppAuthUnstableError, createWaSocket, createWhatsAppLoginTool, extractContactContext, extractLocationData, extractMediaPlaceholder, extractText, formatError, formatWhatsAppWebAuthStatusState, getActiveWebListener, getDefaultLocalRoots, getStatusCode, getWebAuthAgeMs, handleWhatsAppAction, hasWebCredsSync, loadWebMedia, loadWebMediaRaw, logWebSelfId, loginWeb, logoutWeb, monitorWebChannel, monitorWebInbox, newConnectionId, optimizeImageToJpeg, optimizeImageToPng, pickWebChannel, readCredsJsonRaw, readWebAuthExistsBestEffort, readWebAuthExistsForDecision, readWebAuthSnapshot, readWebAuthSnapshotBestEffort, readWebAuthState, readWebSelfId, readWebSelfIdentity, readWebSelfIdentityForDecision, resetWebInboundDedupe, resolveDefaultWebAuthDir, resolveWebAccountId, resolveWebCredsBackupPath, resolveWebCredsPath, restoreCredsFromBackupIfNeeded, sendMessageWhatsApp, sendPollWhatsApp, sendReactionWhatsApp, sendTypingWhatsApp, setWhatsAppRuntime, startWebLoginWithQr, stripHeartbeatToken, waitForCredsSaveQueue, waitForCredsSaveQueueWithTimeout, waitForWaConnection, waitForWebLogin, webAuthExists, whatsAppActionRuntime, writeCredsJsonAtomically };
@@ -6,7 +6,7 @@ import "./normalize-Bxwqo-bW.js";
6
6
  import { t as getOptionalWhatsAppRuntime } from "./runtime-BfAdAEYT.js";
7
7
  import { r as getRegisteredWhatsAppConnectionController, t as formatError } from "./session-errors-CbsoQqoy.js";
8
8
  import { r as isWhatsAppSocketOperationTimeoutError } from "./socket-timing-DvMNkIge.js";
9
- import { a as sanitizeAssistantVisibleTextWithProfile, d as markdownToWhatsApp, i as sanitizeAssistantVisibleText, o as sleep, p as toWhatsappJid, s as stripToolCallXmlTags } from "./text-runtime-BBSmIBHN.js";
9
+ import { a as sanitizeAssistantVisibleTextWithProfile, d as markdownToWhatsApp, i as sanitizeAssistantVisibleText, m as toWhatsappJid, o as sleep, s as stripToolCallXmlTags } from "./text-runtime-CpiloI73.js";
10
10
  import path from "node:path";
11
11
  import { uniqueStrings } from "openclaw/plugin-sdk/string-coerce-runtime";
12
12
  import { sanitizeForPlainText } from "openclaw/plugin-sdk/channel-outbound";
@@ -102,6 +102,10 @@ function buildReactionTargetKey(params) {
102
102
  if (!accountId || !remoteJid || !messageId) return null;
103
103
  return `${accountId}:${remoteJid}:${messageId}`;
104
104
  }
105
+ function addCandidateRemoteJid(target, value) {
106
+ const remoteJid = value?.trim();
107
+ if (remoteJid && !target.includes(remoteJid)) target.push(remoteJid);
108
+ }
105
109
  function reportPersistentApprovalReactionError(error) {
106
110
  try {
107
111
  getOptionalWhatsAppRuntime()?.logging.getChildLogger({
@@ -197,16 +201,42 @@ async function resolveWhatsAppApprovalReactionTargetWithPersistence(params) {
197
201
  reactionKey: params.reactionKey
198
202
  });
199
203
  }
204
+ async function resolveWhatsAppApprovalReactionTargetFromCandidates(params) {
205
+ const candidateRemoteJids = [];
206
+ for (const observedRemoteJid of params.observedRemoteJids) {
207
+ addCandidateRemoteJid(candidateRemoteJids, observedRemoteJid);
208
+ try {
209
+ for (const candidate of await params.resolveReactionTargetJids?.(observedRemoteJid) ?? []) addCandidateRemoteJid(candidateRemoteJids, candidate);
210
+ } catch (error) {
211
+ params.logVerboseMessage?.(`whatsapp: approval reaction target JID mapping failed for ${observedRemoteJid}: ${String(error)}`);
212
+ }
213
+ }
214
+ for (const remoteJid of candidateRemoteJids) {
215
+ const target = await resolveWhatsAppApprovalReactionTargetWithPersistence({
216
+ accountId: params.accountId,
217
+ remoteJid,
218
+ messageId: params.messageId,
219
+ reactionKey: params.reactionKey
220
+ });
221
+ if (target) return {
222
+ ...target,
223
+ remoteJid
224
+ };
225
+ }
226
+ return null;
227
+ }
200
228
  function readWhatsAppApprovalReactionEvent(params) {
201
229
  const msg = params.msg;
202
230
  const reaction = msg.message?.reactionMessage;
203
231
  const reactionKey = reaction?.text?.trim() ?? "";
204
232
  const messageId = reaction?.key?.id?.trim() ?? "";
205
- const remoteJid = (reaction?.key?.remoteJid ?? msg.key?.remoteJid ?? "").trim();
233
+ const remoteJids = [];
234
+ addCandidateRemoteJid(remoteJids, reaction?.key?.remoteJid);
235
+ addCandidateRemoteJid(remoteJids, msg.key?.remoteJid);
206
236
  const actorJid = msg.key?.participant?.trim() || (msg.key?.fromMe ? params.selfLid?.trim() ?? params.selfJid?.trim() ?? "" : msg.key?.remoteJid?.trim() ?? "");
207
- if (!reactionKey || !messageId || !remoteJid || !actorJid) return null;
237
+ if (!reactionKey || !messageId || remoteJids.length === 0 || !actorJid) return null;
208
238
  return {
209
- remoteJid,
239
+ remoteJids,
210
240
  messageId,
211
241
  actorJid,
212
242
  reactionKey
@@ -219,11 +249,13 @@ async function maybeResolveWhatsAppApprovalReaction(params) {
219
249
  selfLid: params.selfLid
220
250
  });
221
251
  if (!event) return false;
222
- const target = await resolveWhatsAppApprovalReactionTargetWithPersistence({
252
+ const target = await resolveWhatsAppApprovalReactionTargetFromCandidates({
223
253
  accountId: params.accountId,
224
- remoteJid: event.remoteJid,
254
+ observedRemoteJids: event.remoteJids,
225
255
  messageId: event.messageId,
226
- reactionKey: event.reactionKey
256
+ reactionKey: event.reactionKey,
257
+ resolveReactionTargetJids: params.resolveReactionTargetJids,
258
+ logVerboseMessage: params.logVerboseMessage
227
259
  });
228
260
  if (!target) return false;
229
261
  const actorId = await params.resolveInboundJid(event.actorJid);
@@ -264,7 +296,7 @@ async function maybeResolveWhatsAppApprovalReaction(params) {
264
296
  if (isApprovalNotFoundError(error)) {
265
297
  unregisterWhatsAppApprovalReactionTarget({
266
298
  accountId: params.accountId,
267
- remoteJid: event.remoteJid,
299
+ remoteJid: target.remoteJid,
268
300
  messageId: event.messageId
269
301
  });
270
302
  params.logVerboseMessage?.(`whatsapp: approval reaction ignored for expired approval id=${target.approvalId} sender=${actorId}`);
@@ -1,9 +1,9 @@
1
1
  import { n as isWhatsAppNewsletterJid } from "./normalize-target-bVWjgftN.js";
2
- import { u as resolveWhatsAppDocumentFileName } from "./send-A9EqsNyz.js";
2
+ import { u as resolveWhatsAppDocumentFileName } from "./send-BplHdEjw.js";
3
3
  import "./normalize-Bxwqo-bW.js";
4
- import { m as toWhatsappJidWithLid, p as toWhatsappJid, u as jidToE164 } from "./text-runtime-BBSmIBHN.js";
5
- import { t as buildQuotedMessageOptions } from "./quoted-message-DVOfpEja.js";
6
- import { c as resolveComparableIdentity } from "./identity-Cm6bKAtk.js";
4
+ import { h as toWhatsappJidWithLid, m as toWhatsappJid, u as jidToE164 } from "./text-runtime-CpiloI73.js";
5
+ import { t as buildQuotedMessageOptions } from "./quoted-message-DqmWlbN7.js";
6
+ import { c as resolveComparableIdentity } from "./identity-DdeafYji.js";
7
7
  import { normalizeLowercaseStringOrEmpty, normalizeStringEntries, uniqueStrings } from "openclaw/plugin-sdk/string-coerce-runtime";
8
8
  import { createMessageReceiptFromOutboundResults, listMessageReceiptPlatformIds } from "openclaw/plugin-sdk/channel-outbound";
9
9
  import { logVerbose } from "openclaw/plugin-sdk/runtime-env";
@@ -1,7 +1,7 @@
1
1
  import { o as resolveWebCredsBackupPath, s as resolveWebCredsPath, t as assertWebCredsPathRegularFileOrMissing } from "./creds-files-B1kSWtBg.js";
2
2
  import { n as getStatusCode } from "./session-errors-CbsoQqoy.js";
3
3
  import { t as DEFAULT_WHATSAPP_SOCKET_TIMING } from "./socket-timing-DvMNkIge.js";
4
- import { E as writeWebCredsRawAtomically, S as enqueueCredsSave, T as writeCredsJsonAtomically, b as restoreCredsFromBackupIfNeeded, u as readCredsJsonRaw, w as waitForCredsSaveQueueWithTimeout, y as resolveDefaultWebAuthDir } from "./auth-store-RyuCPHE0.js";
4
+ import { E as writeWebCredsRawAtomically, S as enqueueCredsSave, T as writeCredsJsonAtomically, b as restoreCredsFromBackupIfNeeded, u as readCredsJsonRaw, w as waitForCredsSaveQueueWithTimeout, y as resolveDefaultWebAuthDir } from "./auth-store-BRv2o3w2.js";
5
5
  import { i as makeWASocket, n as fetchLatestBaileysVersion, o as useMultiFileAuthState, r as makeCacheableSignalKeyStore } from "./session.runtime-CyooSQvj.js";
6
6
  import { VERSION, formatCliCommand } from "openclaw/plugin-sdk/cli-runtime";
7
7
  import { danger, getChildLogger, success, toPinoLikeLogger } from "openclaw/plugin-sdk/runtime-env";
@@ -90,7 +90,9 @@ async function createWaSocket(printQr, verbose, opts = {}) {
90
90
  markOnlineOnConnect: false,
91
91
  ...socketTiming,
92
92
  agent,
93
- fetchAgent
93
+ fetchAgent,
94
+ ...opts.getMessage ? { getMessage: opts.getMessage } : {},
95
+ ...opts.cachedGroupMetadata ? { cachedGroupMetadata: opts.cachedGroupMetadata } : {}
94
96
  });
95
97
  sock.ev.on("creds.update", () => enqueueSaveCreds(authDir, saveCreds, sessionLogger));
96
98
  sock.ev.on("connection.update", (update) => {
@@ -99,10 +99,10 @@ async function applyWhatsAppSecurityConfigFixes(params) {
99
99
  //#region extensions/whatsapp/src/shared.ts
100
100
  const WHATSAPP_CHANNEL = "whatsapp";
101
101
  async function loadWhatsAppChannelRuntime() {
102
- return await import("./channel.runtime-ZKS2C0Cw.js");
102
+ return await import("./channel.runtime-kVF_UONw.js");
103
103
  }
104
104
  async function loadWhatsAppSetupSurface() {
105
- return await import("./setup-surface-ByAUWXyq.js");
105
+ return await import("./setup-surface-BpdIDwDg.js");
106
106
  }
107
107
  const whatsappSetupWizardProxy = createWhatsAppSetupWizardProxy(async () => (await loadWhatsAppSetupSurface()).whatsappSetupWizard);
108
108
  const whatsappConfigAdapter = createScopedChannelConfigAdapter({
@@ -2,7 +2,7 @@ import { r as resolveDefaultWhatsAppAccountId } from "./account-ids-CB5SOWjc.js"
2
2
  import { r as hasWebCredsSync } from "./creds-files-B1kSWtBg.js";
3
3
  import { a as resolveWhatsAppAccount, o as resolveWhatsAppAuthDir } from "./accounts-DgViSyJx.js";
4
4
  import { a as normalizeWhatsAppAllowFromEntries, o as normalizeWhatsAppAllowFromEntry } from "./normalize-target-bVWjgftN.js";
5
- import { t as whatsappSetupAdapter } from "./setup-core-DVEkfMVh.js";
5
+ import { t as whatsappSetupAdapter } from "./setup-core-D0JxJ53T.js";
6
6
  import { DEFAULT_ACCOUNT_ID, createSetupTranslator, splitSetupEntries } from "openclaw/plugin-sdk/setup";
7
7
  import { formatCliCommand, formatDocsLink } from "openclaw/plugin-sdk/setup-tools";
8
8
  //#region extensions/whatsapp/src/setup-finalize.ts
@@ -280,7 +280,7 @@ async function finalizeWhatsAppSetup(params) {
280
280
  message: linked ? t("wizard.whatsapp.relinkPrompt") : t("wizard.whatsapp.linkNowPrompt"),
281
281
  initialValue: !linked
282
282
  })) try {
283
- const { loginWeb } = await import("./login-B503Fwb8.js").then((n) => n.n);
283
+ const { loginWeb } = await import("./login-FpqysWi0.js").then((n) => n.n);
284
284
  await loginWeb(false, void 0, params.runtime, accountId);
285
285
  } catch (error) {
286
286
  params.runtime.error(`WhatsApp login failed: ${String(error)}`);
@@ -1,2 +1,2 @@
1
- import { t as whatsappSetupPlugin } from "./channel.setup-BfcLCLNn.js";
1
+ import { t as whatsappSetupPlugin } from "./channel.setup-BTi6IdDT.js";
2
2
  export { whatsappSetupPlugin };
@@ -1,6 +1,6 @@
1
1
  import { t as listAccountIds } from "./account-ids-CB5SOWjc.js";
2
2
  import { o as resolveWhatsAppAuthDir } from "./accounts-DgViSyJx.js";
3
- import { a as formatWhatsAppWebAuthStatusState, h as readWebAuthState } from "./auth-store-RyuCPHE0.js";
3
+ import { a as formatWhatsAppWebAuthStatusState, h as readWebAuthState } from "./auth-store-BRv2o3w2.js";
4
4
  import { DEFAULT_ACCOUNT_ID, createSetupTranslator, setSetupChannelEnabled } from "openclaw/plugin-sdk/setup";
5
5
  //#region extensions/whatsapp/src/setup-surface.ts
6
6
  const t = createSetupTranslator();
@@ -36,7 +36,7 @@ const whatsappSetupWizard = {
36
36
  },
37
37
  resolveShouldPromptAccountIds: ({ shouldPromptAccountIds }) => shouldPromptAccountIds,
38
38
  credentials: [],
39
- finalize: async (params) => await (await import("./setup-finalize-DJepnx7S.js")).finalizeWhatsAppSetup(params),
39
+ finalize: async (params) => await (await import("./setup-finalize-BRTq3uPs.js")).finalizeWhatsAppSetup(params),
40
40
  disable: (cfg) => setSetupChannelEnabled(cfg, channel, false),
41
41
  onAccountRecorded: (accountId, options) => {
42
42
  options?.onAccountId?.(channel, accountId);
@@ -39,6 +39,58 @@ function toWhatsappJidWithLid(number, opts) {
39
39
  });
40
40
  return lid ? `${lid}@lid` : `${phoneDigits}@s.whatsapp.net`;
41
41
  }
42
+ function addUniqueString(target, value) {
43
+ const normalized = value?.trim();
44
+ if (normalized && !target.includes(normalized)) target.push(normalized);
45
+ }
46
+ async function tryLookupMappedJid(lookup) {
47
+ if (!lookup) return null;
48
+ try {
49
+ return await lookup() ?? null;
50
+ } catch (err) {
51
+ if (shouldLogVerbose()) logVerbose(`LID mapping lookup failed: ${String(err)}`);
52
+ return null;
53
+ }
54
+ }
55
+ const DIRECT_PN_JID_RE = /^(\d+)(?::\d+)?@(s\.whatsapp\.net|hosted)$/i;
56
+ const DIRECT_LID_JID_RE = /^(\d+)(?::\d+)?@(lid|hosted\.lid)$/i;
57
+ function addEquivalentDirectChatCandidate(target, jid) {
58
+ addUniqueString(target, jid);
59
+ const pnMatch = jid?.match(DIRECT_PN_JID_RE);
60
+ if (pnMatch) {
61
+ addUniqueString(target, `${pnMatch[1]}@${pnMatch[2]}`);
62
+ return;
63
+ }
64
+ const lidMatch = jid?.match(DIRECT_LID_JID_RE);
65
+ if (lidMatch) addUniqueString(target, `${lidMatch[1]}@${lidMatch[2]}`);
66
+ }
67
+ async function resolveEquivalentWhatsAppDirectChatJids(jid, opts) {
68
+ const normalized = jid?.trim();
69
+ if (!normalized) return [];
70
+ const candidates = [];
71
+ addEquivalentDirectChatCandidate(candidates, normalized);
72
+ const pnMatch = normalized.match(DIRECT_PN_JID_RE);
73
+ if (pnMatch) {
74
+ addEquivalentDirectChatCandidate(candidates, await tryLookupMappedJid(() => opts?.lidLookup?.getLIDForPN?.(normalized)));
75
+ const mappedLocalLid = readLidForwardMapping({
76
+ phoneDigits: pnMatch[1],
77
+ opts
78
+ });
79
+ const localLidDomain = pnMatch[2].toLowerCase() === "hosted" ? "hosted.lid" : "lid";
80
+ addUniqueString(candidates, mappedLocalLid ? `${mappedLocalLid}@${localLidDomain}` : null);
81
+ return candidates;
82
+ }
83
+ const lidMatch = normalized.match(DIRECT_LID_JID_RE);
84
+ if (lidMatch) {
85
+ addEquivalentDirectChatCandidate(candidates, await tryLookupMappedJid(() => opts?.lidLookup?.getPNForLID?.(normalized)));
86
+ const e164 = jidToE164(normalized, {
87
+ ...opts,
88
+ logMissing: false
89
+ });
90
+ addUniqueString(candidates, e164 && lidMatch[2].toLowerCase() === "hosted.lid" ? `${e164.replace(/\D/g, "")}@hosted` : e164 ? toWhatsappJid(e164) : null);
91
+ }
92
+ return candidates;
93
+ }
42
94
  function resolveLidMappingDirs(params) {
43
95
  const dirs = /* @__PURE__ */ new Set();
44
96
  const addDir = (dir) => {
@@ -128,4 +180,4 @@ function markdownToWhatsApp(text) {
128
180
  return result;
129
181
  }
130
182
  //#endregion
131
- export { sanitizeAssistantVisibleTextWithProfile as a, assertWebChannel as c, markdownToWhatsApp as d, resolveJidToE164 as f, sanitizeAssistantVisibleText as i, isSelfChatMode as l, toWhatsappJidWithLid as m, normalizeE164$1 as n, sleep as o, toWhatsappJid as p, resolveUserPath$2 as r, stripToolCallXmlTags as s, convertMarkdownTables as t, jidToE164 as u };
183
+ export { sanitizeAssistantVisibleTextWithProfile as a, assertWebChannel as c, markdownToWhatsApp as d, resolveEquivalentWhatsAppDirectChatJids as f, toWhatsappJidWithLid as h, sanitizeAssistantVisibleText as i, isSelfChatMode as l, toWhatsappJid as m, normalizeE164$1 as n, sleep as o, resolveJidToE164 as p, resolveUserPath$2 as r, stripToolCallXmlTags as s, convertMarkdownTables as t, jidToE164 as u };
@@ -1,19 +1,19 @@
1
1
  {
2
2
  "name": "@openclaw/whatsapp",
3
- "version": "2026.6.10",
3
+ "version": "2026.6.11-beta.2",
4
4
  "lockfileVersion": 3,
5
5
  "requires": true,
6
6
  "packages": {
7
7
  "": {
8
8
  "name": "@openclaw/whatsapp",
9
- "version": "2026.6.10",
9
+ "version": "2026.6.11-beta.2",
10
10
  "dependencies": {
11
11
  "audio-decode": "2.2.3",
12
12
  "baileys": "7.0.0-rc13",
13
13
  "typebox": "1.1.39"
14
14
  },
15
15
  "peerDependencies": {
16
- "openclaw": ">=2026.6.10"
16
+ "openclaw": ">=2026.6.11-beta.2"
17
17
  },
18
18
  "peerDependenciesMeta": {
19
19
  "openclaw": {
@@ -2,6 +2,10 @@
2
2
  "id": "whatsapp",
3
3
  "name": "WhatsApp",
4
4
  "description": "OpenClaw WhatsApp channel plugin for WhatsApp Web chats.",
5
+ "icon": "https://cdn.simpleicons.org/whatsapp",
6
+ "skills": [
7
+ "./skills"
8
+ ],
5
9
  "activation": {
6
10
  "onStartup": false
7
11
  },
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@openclaw/whatsapp",
3
- "version": "2026.6.10",
3
+ "version": "2026.6.11-beta.2",
4
4
  "description": "OpenClaw WhatsApp channel plugin for WhatsApp Web chats.",
5
5
  "repository": {
6
6
  "type": "git",
@@ -13,7 +13,7 @@
13
13
  "typebox": "1.1.39"
14
14
  },
15
15
  "peerDependencies": {
16
- "openclaw": ">=2026.6.10"
16
+ "openclaw": ">=2026.6.11-beta.2"
17
17
  },
18
18
  "peerDependenciesMeta": {
19
19
  "openclaw": {
@@ -56,10 +56,10 @@
56
56
  "minHostVersion": ">=2026.4.25"
57
57
  },
58
58
  "compat": {
59
- "pluginApi": ">=2026.6.10"
59
+ "pluginApi": ">=2026.6.11-beta.2"
60
60
  },
61
61
  "build": {
62
- "openclawVersion": "2026.6.10"
62
+ "openclawVersion": "2026.6.11-beta.2"
63
63
  },
64
64
  "release": {
65
65
  "publishToClawHub": true,
@@ -74,7 +74,8 @@
74
74
  "dist/**",
75
75
  "openclaw.plugin.json",
76
76
  "npm-shrinkwrap.json",
77
- "README.md"
77
+ "README.md",
78
+ "skills/**"
78
79
  ],
79
80
  "bundledDependencies": [
80
81
  "audio-decode",
@@ -0,0 +1,72 @@
1
+ ---
2
+ name: wacli
3
+ description: "Send third-party WhatsApp messages or sync/search WhatsApp history via wacli, not normal active chats."
4
+ homepage: https://wacli.sh
5
+ metadata:
6
+ {
7
+ "openclaw":
8
+ {
9
+ "emoji": "📱",
10
+ "requires": { "bins": ["wacli"] },
11
+ "install":
12
+ [
13
+ {
14
+ "id": "brew",
15
+ "kind": "brew",
16
+ "formula": "steipete/tap/wacli",
17
+ "bins": ["wacli"],
18
+ "label": "Install wacli (brew)",
19
+ },
20
+ {
21
+ "id": "go",
22
+ "kind": "go",
23
+ "module": "github.com/steipete/wacli/cmd/wacli@latest",
24
+ "bins": ["wacli"],
25
+ "label": "Install wacli (go)",
26
+ },
27
+ ],
28
+ },
29
+ }
30
+ ---
31
+
32
+ # wacli
33
+
34
+ Use `wacli` only when the user explicitly asks you to message someone else on WhatsApp or when they ask to sync/search WhatsApp history.
35
+ Do NOT use `wacli` for normal user chats; OpenClaw routes WhatsApp conversations automatically.
36
+ If the user is chatting with you on WhatsApp, you should not reach for this tool unless they ask you to contact a third party.
37
+
38
+ Safety
39
+
40
+ - Require explicit recipient + message text.
41
+ - Confirm recipient + message before sending.
42
+ - If anything is ambiguous, ask a clarifying question.
43
+
44
+ Auth + sync
45
+
46
+ - `wacli auth` (QR login + initial sync)
47
+ - `wacli sync --follow` (continuous sync)
48
+ - `wacli doctor`
49
+
50
+ Find chats + messages
51
+
52
+ - `wacli chats list --limit 20 --query "name or number"`
53
+ - `wacli messages search "query" --limit 20 --chat <jid>`
54
+ - `wacli messages search "invoice" --after 2025-01-01 --before 2025-12-31`
55
+
56
+ History backfill
57
+
58
+ - `wacli history backfill --chat <jid> --requests 2 --count 50`
59
+
60
+ Send
61
+
62
+ - Text: `wacli send text --to "+14155551212" --message "Hello! Are you free at 3pm?"`
63
+ - Group: `wacli send text --to "1234567890-123456789@g.us" --message "Running 5 min late."`
64
+ - File: `wacli send file --to "+14155551212" --file /path/agenda.pdf --caption "Agenda"`
65
+
66
+ Notes
67
+
68
+ - Store dir: `~/.wacli` (override with `--store`).
69
+ - Use `--json` for machine-readable output when parsing.
70
+ - Backfill requires your phone online; results are best-effort.
71
+ - WhatsApp CLI is not needed for routine user chats; it's for messaging other people.
72
+ - JIDs: direct chats look like `<number>@s.whatsapp.net`; groups look like `<id>@g.us` (use `wacli chats list` to find).