@0xmaxma/claude-gateway 1.8.13 → 1.8.14
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.
- package/README.md +8 -0
- package/dist/agent/runner.d.ts +17 -0
- package/dist/agent/runner.d.ts.map +1 -1
- package/dist/agent/runner.js +187 -14
- package/dist/agent/runner.js.map +1 -1
- package/dist/api/router.d.ts.map +1 -1
- package/dist/api/router.js +237 -1
- package/dist/api/router.js.map +1 -1
- package/dist/api/wechat-access.d.ts +45 -0
- package/dist/api/wechat-access.d.ts.map +1 -0
- package/dist/api/wechat-access.js +48 -0
- package/dist/api/wechat-access.js.map +1 -0
- package/dist/history/types.d.ts +10 -1
- package/dist/history/types.d.ts.map +1 -1
- package/dist/history/types.js +10 -1
- package/dist/history/types.js.map +1 -1
- package/dist/session/process.d.ts.map +1 -1
- package/dist/session/process.js +1 -0
- package/dist/session/process.js.map +1 -1
- package/dist/types.d.ts +40 -0
- package/dist/types.d.ts.map +1 -1
- package/dist/wechat/ilink-client.d.ts +194 -0
- package/dist/wechat/ilink-client.d.ts.map +1 -0
- package/dist/wechat/ilink-client.js +641 -0
- package/dist/wechat/ilink-client.js.map +1 -0
- package/dist/wechat/manager.d.ts +93 -0
- package/dist/wechat/manager.d.ts.map +1 -0
- package/dist/wechat/manager.js +409 -0
- package/dist/wechat/manager.js.map +1 -0
- package/mcp/server.ts +2 -0
- package/mcp/tools/wechat/client.ts +49 -0
- package/mcp/tools/wechat/module.ts +88 -0
- package/package.json +1 -1
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"ilink-client.js","sourceRoot":"","sources":["../../src/wechat/ilink-client.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,93 @@
|
|
|
1
|
+
import { AgentConfig } from '../types';
|
|
2
|
+
import { ILinkClient, ILinkUpdate } from './ilink-client';
|
|
3
|
+
export type WeChatLinkStatus = 'unlinked' | 'pending_scan' | 'linked' | 'reconnecting';
|
|
4
|
+
export interface WeChatStatus {
|
|
5
|
+
status: WeChatLinkStatus;
|
|
6
|
+
/** Data URI to render while `status === 'pending_scan'`. */
|
|
7
|
+
qr?: string;
|
|
8
|
+
/** Session was invalidated remotely (WeChat logged this device out). */
|
|
9
|
+
loggedOut: boolean;
|
|
10
|
+
}
|
|
11
|
+
/** Directory name for this channel's on-disk session file, relative to the agent workspace. */
|
|
12
|
+
export declare const WECHAT_STATE_DIR = ".wechat-state";
|
|
13
|
+
/** iLink's documented per-message character limit (Hermes-agent doc). */
|
|
14
|
+
export declare const WECHAT_MAX_MESSAGE_LENGTH = 4000;
|
|
15
|
+
/** Delay between outbound chunks, per iLink's documented rate-limit guidance. */
|
|
16
|
+
export declare const WECHAT_CHUNK_DELAY_MS = 300;
|
|
17
|
+
/** Timing knobs, overridable in tests so the suite doesn't depend on real wall-clock delays. */
|
|
18
|
+
export interface WeChatManagerTiming {
|
|
19
|
+
pollTimeoutSeconds: number;
|
|
20
|
+
/** Flat retry delay for the first `pollMaxConsecutiveFailures` getUpdates failures in a row. */
|
|
21
|
+
pollRetryDelayMs: number;
|
|
22
|
+
/** Fixed pause once `pollMaxConsecutiveFailures` failures happen consecutively — then the counter resets. */
|
|
23
|
+
pollBackoffDelayMs: number;
|
|
24
|
+
pollMaxConsecutiveFailures: number;
|
|
25
|
+
linkAttemptTimeoutMs: number;
|
|
26
|
+
linkPollIntervalMs: number;
|
|
27
|
+
/**
|
|
28
|
+
* Minimum pacing between successful `getUpdates` calls. iLink's real
|
|
29
|
+
* `getupdates` blocks for up to `pollTimeoutSeconds` on its own, so this is
|
|
30
|
+
* 0 in production — it exists so a test double that resolves instantly
|
|
31
|
+
* can't spin the loop into a memory-exhausting busy-loop (every call is
|
|
32
|
+
* recorded by the mock framework).
|
|
33
|
+
*/
|
|
34
|
+
pollIdleDelayMs: number;
|
|
35
|
+
}
|
|
36
|
+
/** Split outbound text at iLink's documented 4000-char limit, on whole lines where possible. */
|
|
37
|
+
export declare function chunkWeChatText(text: string): string[];
|
|
38
|
+
export declare function isWeChatChannelEnabled(): boolean;
|
|
39
|
+
export declare class WeChatManager {
|
|
40
|
+
private agentConfig;
|
|
41
|
+
private readonly client;
|
|
42
|
+
/** Called once per new inbound message, after de-dup — never for a retried delivery. */
|
|
43
|
+
private readonly onMessage?;
|
|
44
|
+
private readonly timing;
|
|
45
|
+
private status;
|
|
46
|
+
private qrDataUri;
|
|
47
|
+
private loggedOut;
|
|
48
|
+
private stopping;
|
|
49
|
+
private credentials;
|
|
50
|
+
private contextTokens;
|
|
51
|
+
private readonly stateFile;
|
|
52
|
+
private readonly logger;
|
|
53
|
+
private readonly recentMessageIds;
|
|
54
|
+
private readonly recentMessageOrder;
|
|
55
|
+
private pollLoopPromise;
|
|
56
|
+
private pollGeneration;
|
|
57
|
+
constructor(agentConfig: AgentConfig, logDir: string, client?: ILinkClient,
|
|
58
|
+
/** Called once per new inbound message, after de-dup — never for a retried delivery. */
|
|
59
|
+
onMessage?: ((update: ILinkUpdate) => void) | undefined, timing?: WeChatManagerTiming);
|
|
60
|
+
updateAgentConfig(newConfig: AgentConfig): void;
|
|
61
|
+
getStatus(): WeChatStatus;
|
|
62
|
+
/** Resume a previously-linked session on gateway boot — no-op if never linked. */
|
|
63
|
+
resumeIfLinked(): Promise<void>;
|
|
64
|
+
/**
|
|
65
|
+
* Start a fresh QR-code linking flow. Blocked only if an admin has set
|
|
66
|
+
* `WECHAT_CHANNEL_DISABLED` — the hard kill switch for a third-party
|
|
67
|
+
* dependency no deployer of this gateway controls (see module doc comment).
|
|
68
|
+
*/
|
|
69
|
+
startLinking(): Promise<void>;
|
|
70
|
+
/** Logout and wipe the linked session. The user must scan fresh afterward. */
|
|
71
|
+
unlink(): Promise<void>;
|
|
72
|
+
/**
|
|
73
|
+
* Send a single outbound message, chunked over iLink's 4000-char limit with
|
|
74
|
+
* the documented 0.3s inter-chunk delay. Media is out of scope for v1 (see
|
|
75
|
+
* the plan's non-goals) — text only.
|
|
76
|
+
*
|
|
77
|
+
* `contextToken` is NOT refreshed here — per Tencent's real protocol
|
|
78
|
+
* (confirmed against `Tencent/openclaw-weixin`'s own doc), the token flows
|
|
79
|
+
* the other way: an INBOUND message establishes it (captured in
|
|
80
|
+
* `runPollLoop` below), and every subsequent send to that sender echoes
|
|
81
|
+
* whatever was captured last. `sendmessage`'s own response carries no
|
|
82
|
+
* token to update.
|
|
83
|
+
*/
|
|
84
|
+
sendMessage(toId: string, text: string): Promise<void>;
|
|
85
|
+
private startPollLoop;
|
|
86
|
+
private runPollLoop;
|
|
87
|
+
private isDuplicate;
|
|
88
|
+
private rememberMessage;
|
|
89
|
+
private readSession;
|
|
90
|
+
private persistSession;
|
|
91
|
+
}
|
|
92
|
+
export declare function hasSavedWeChatSession(workspace: string): boolean;
|
|
93
|
+
//# sourceMappingURL=manager.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"manager.d.ts","sourceRoot":"","sources":["../../src/wechat/manager.ts"],"names":[],"mappings":"AAmCA,OAAO,EAAE,WAAW,EAAE,MAAM,UAAU,CAAC;AAEvC,OAAO,EACL,WAAW,EAEX,WAAW,EAEZ,MAAM,gBAAgB,CAAC;AAExB,MAAM,MAAM,gBAAgB,GAAG,UAAU,GAAG,cAAc,GAAG,QAAQ,GAAG,cAAc,CAAC;AAEvF,MAAM,WAAW,YAAY;IAC3B,MAAM,EAAE,gBAAgB,CAAC;IACzB,4DAA4D;IAC5D,EAAE,CAAC,EAAE,MAAM,CAAC;IACZ,wEAAwE;IACxE,SAAS,EAAE,OAAO,CAAC;CACpB;AAED,+FAA+F;AAC/F,eAAO,MAAM,gBAAgB,kBAAkB,CAAC;AAEhD,yEAAyE;AACzE,eAAO,MAAM,yBAAyB,OAAO,CAAC;AAE9C,iFAAiF;AACjF,eAAO,MAAM,qBAAqB,MAAM,CAAC;AA8BzC,gGAAgG;AAChG,MAAM,WAAW,mBAAmB;IAClC,kBAAkB,EAAE,MAAM,CAAC;IAC3B,gGAAgG;IAChG,gBAAgB,EAAE,MAAM,CAAC;IACzB,6GAA6G;IAC7G,kBAAkB,EAAE,MAAM,CAAC;IAC3B,0BAA0B,EAAE,MAAM,CAAC;IACnC,oBAAoB,EAAE,MAAM,CAAC;IAC7B,kBAAkB,EAAE,MAAM,CAAC;IAC3B;;;;;;OAMG;IACH,eAAe,EAAE,MAAM,CAAC;CACzB;AAYD,gGAAgG;AAChG,wBAAgB,eAAe,CAAC,IAAI,EAAE,MAAM,GAAG,MAAM,EAAE,CAYtD;AAED,wBAAgB,sBAAsB,IAAI,OAAO,CAEhD;AAYD,qBAAa,aAAa;IAetB,OAAO,CAAC,WAAW;IAEnB,OAAO,CAAC,QAAQ,CAAC,MAAM;IACvB,wFAAwF;IACxF,OAAO,CAAC,QAAQ,CAAC,SAAS,CAAC;IAC3B,OAAO,CAAC,QAAQ,CAAC,MAAM;IAnBzB,OAAO,CAAC,MAAM,CAAgC;IAC9C,OAAO,CAAC,SAAS,CAAqB;IACtC,OAAO,CAAC,SAAS,CAAS;IAC1B,OAAO,CAAC,QAAQ,CAAS;IACzB,OAAO,CAAC,WAAW,CAA+B;IAClD,OAAO,CAAC,aAAa,CAA8B;IACnD,OAAO,CAAC,QAAQ,CAAC,SAAS,CAAS;IACnC,OAAO,CAAC,QAAQ,CAAC,MAAM,CAAkC;IACzD,OAAO,CAAC,QAAQ,CAAC,gBAAgB,CAAqB;IACtD,OAAO,CAAC,QAAQ,CAAC,kBAAkB,CAAgB;IACnD,OAAO,CAAC,eAAe,CAA4B;IACnD,OAAO,CAAC,cAAc,CAAK;gBAGjB,WAAW,EAAE,WAAW,EAChC,MAAM,EAAE,MAAM,EACG,MAAM,GAAE,WAAiE;IAC1F,wFAAwF;IACvE,SAAS,CAAC,GAAE,CAAC,MAAM,EAAE,WAAW,KAAK,IAAI,aAAA,EACzC,MAAM,GAAE,mBAAoC;IAM/D,iBAAiB,CAAC,SAAS,EAAE,WAAW,GAAG,IAAI;IAI/C,SAAS,IAAI,YAAY;IAIzB,kFAAkF;IAC5E,cAAc,IAAI,OAAO,CAAC,IAAI,CAAC;IAWrC;;;;OAIG;IACG,YAAY,IAAI,OAAO,CAAC,IAAI,CAAC;IA6DnC,8EAA8E;IACxE,MAAM,IAAI,OAAO,CAAC,IAAI,CAAC;IAoB7B;;;;;;;;;;;OAWG;IACG,WAAW,CAAC,IAAI,EAAE,MAAM,EAAE,IAAI,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC;IAgB5D,OAAO,CAAC,aAAa;YAKP,WAAW;IA0EzB,OAAO,CAAC,WAAW;IAInB,OAAO,CAAC,eAAe;YAST,WAAW;YASX,cAAc;CAO7B;AAQD,wBAAgB,qBAAqB,CAAC,SAAS,EAAE,MAAM,GAAG,OAAO,CAEhE"}
|
|
@@ -0,0 +1,409 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
|
|
3
|
+
if (k2 === undefined) k2 = k;
|
|
4
|
+
var desc = Object.getOwnPropertyDescriptor(m, k);
|
|
5
|
+
if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
|
|
6
|
+
desc = { enumerable: true, get: function() { return m[k]; } };
|
|
7
|
+
}
|
|
8
|
+
Object.defineProperty(o, k2, desc);
|
|
9
|
+
}) : (function(o, m, k, k2) {
|
|
10
|
+
if (k2 === undefined) k2 = k;
|
|
11
|
+
o[k2] = m[k];
|
|
12
|
+
}));
|
|
13
|
+
var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
|
|
14
|
+
Object.defineProperty(o, "default", { enumerable: true, value: v });
|
|
15
|
+
}) : function(o, v) {
|
|
16
|
+
o["default"] = v;
|
|
17
|
+
});
|
|
18
|
+
var __importStar = (this && this.__importStar) || (function () {
|
|
19
|
+
var ownKeys = function(o) {
|
|
20
|
+
ownKeys = Object.getOwnPropertyNames || function (o) {
|
|
21
|
+
var ar = [];
|
|
22
|
+
for (var k in o) if (Object.prototype.hasOwnProperty.call(o, k)) ar[ar.length] = k;
|
|
23
|
+
return ar;
|
|
24
|
+
};
|
|
25
|
+
return ownKeys(o);
|
|
26
|
+
};
|
|
27
|
+
return function (mod) {
|
|
28
|
+
if (mod && mod.__esModule) return mod;
|
|
29
|
+
var result = {};
|
|
30
|
+
if (mod != null) for (var k = ownKeys(mod), i = 0; i < k.length; i++) if (k[i] !== "default") __createBinding(result, mod, k[i]);
|
|
31
|
+
__setModuleDefault(result, mod);
|
|
32
|
+
return result;
|
|
33
|
+
};
|
|
34
|
+
})();
|
|
35
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
36
|
+
exports.WeChatManager = exports.WECHAT_CHUNK_DELAY_MS = exports.WECHAT_MAX_MESSAGE_LENGTH = exports.WECHAT_STATE_DIR = void 0;
|
|
37
|
+
exports.chunkWeChatText = chunkWeChatText;
|
|
38
|
+
exports.isWeChatChannelEnabled = isWeChatChannelEnabled;
|
|
39
|
+
exports.hasSavedWeChatSession = hasSavedWeChatSession;
|
|
40
|
+
/**
|
|
41
|
+
* WeChatManager — one instance per agent, owning that agent's link to a
|
|
42
|
+
* single personal WeChat account through Tencent's iLink Bot API ("WeChat
|
|
43
|
+
* ClawBot" — see src/wechat/ilink-client.ts's doc comment: this is Tencent's
|
|
44
|
+
* own self-serve product, `Tencent/openclaw-weixin` on GitHub, not a
|
|
45
|
+
* third-party grey-market bridge as first assumed during research).
|
|
46
|
+
*
|
|
47
|
+
* Deliberately NOT modeled on a persistent-socket channel (there is no
|
|
48
|
+
* WeChat equivalent of Discord's gateway connection or WhatsApp's Baileys
|
|
49
|
+
* socket in this codebase). iLink delivers messages via long-polling
|
|
50
|
+
* (`getupdates`, 35s timeout, confirmed against Tencent's own protocol doc)
|
|
51
|
+
* — there is also no existing hand-rolled long-poll loop to copy in this
|
|
52
|
+
* codebase; Telegram's polling lives inside the external `claude --channels`
|
|
53
|
+
* CLI, not here. The loop below is the new piece.
|
|
54
|
+
*
|
|
55
|
+
* What IS reused from existing channels:
|
|
56
|
+
* - The QR/status state machine shape (`status`/`qr`/`loggedOut`) mirrors
|
|
57
|
+
* every device-linked channel's UX contract, kept intentionally small
|
|
58
|
+
* since WeChat (unlike WhatsApp/Baileys) has no pairing-code option and
|
|
59
|
+
* no multi-account support in v1.
|
|
60
|
+
* - `WECHAT_CHANNEL_DISABLED` is a hard kill switch, enabled by default (like
|
|
61
|
+
* every other channel here — WhatsApp's own unofficial Baileys bridge has
|
|
62
|
+
* no equivalent gate; a user linking via QR is already the informed
|
|
63
|
+
* consent). Opt-OUT rather than opt-IN deliberately: an opt-in flag would
|
|
64
|
+
* silently break WeChat for every existing deployer on their first update
|
|
65
|
+
* after this channel ships, since nothing prompts them to set it. The
|
|
66
|
+
* escape hatch still exists because, even though this is Tencent's own
|
|
67
|
+
* product, no deployer of this gateway controls it (protocol changes, the
|
|
68
|
+
* undocumented `need_verifycode`/`verify_code_blocked` states this
|
|
69
|
+
* integration can't yet act on, etc.) — an admin who hits one of those can
|
|
70
|
+
* kill the whole channel with one env var and no redeploy of manager logic.
|
|
71
|
+
*/
|
|
72
|
+
const fs = __importStar(require("fs"));
|
|
73
|
+
const fsp = __importStar(require("fs/promises"));
|
|
74
|
+
const path = __importStar(require("path"));
|
|
75
|
+
const logger_1 = require("../logger");
|
|
76
|
+
const ilink_client_1 = require("./ilink-client");
|
|
77
|
+
/** Directory name for this channel's on-disk session file, relative to the agent workspace. */
|
|
78
|
+
exports.WECHAT_STATE_DIR = '.wechat-state';
|
|
79
|
+
/** iLink's documented per-message character limit (Hermes-agent doc). */
|
|
80
|
+
exports.WECHAT_MAX_MESSAGE_LENGTH = 4000;
|
|
81
|
+
/** Delay between outbound chunks, per iLink's documented rate-limit guidance. */
|
|
82
|
+
exports.WECHAT_CHUNK_DELAY_MS = 300;
|
|
83
|
+
/** `getupdates` long-poll timeout, per the iLink contract both source docs describe. */
|
|
84
|
+
const POLL_TIMEOUT_SECONDS = 35;
|
|
85
|
+
/**
|
|
86
|
+
* getUpdates failure handling — deliberately NOT exponential backoff.
|
|
87
|
+
* Matches Tencent's own official client (`Tencent/openclaw-weixin`'s
|
|
88
|
+
* `src/monitor/monitor.ts`, confirmed live 2026-09-10) exactly: a short flat
|
|
89
|
+
* retry for the first few failures, one fixed pause after
|
|
90
|
+
* `POLL_MAX_CONSECUTIVE_FAILURES` in a row, then reset back to fast retries.
|
|
91
|
+
* An earlier exponential-backoff version of this (1s→2s→4s...capped at 30s,
|
|
92
|
+
* NEVER resetting while failures continued) starved the poll loop of
|
|
93
|
+
* attempts during a real live test: the endpoint returns Cloudflare 522/524
|
|
94
|
+
* on the large majority of idle long-polls (confirmed via direct curl
|
|
95
|
+
* outside this codebase too — it's Tencent/Cloudflare-side flakiness, not a
|
|
96
|
+
* bug here), so how OFTEN we retry directly determines whether a queued
|
|
97
|
+
* message actually gets picked up in a timely way.
|
|
98
|
+
*/
|
|
99
|
+
const POLL_RETRY_DELAY_MS = 2000;
|
|
100
|
+
const POLL_BACKOFF_DELAY_MS = 30000;
|
|
101
|
+
const POLL_MAX_CONSECUTIVE_FAILURES = 3;
|
|
102
|
+
/** How long a QR login attempt stays valid before `startLinking()` must be called again. */
|
|
103
|
+
const LINK_ATTEMPT_TIMEOUT_MS = 2 * 60 * 1000;
|
|
104
|
+
const LINK_POLL_INTERVAL_MS = 2000;
|
|
105
|
+
/** Recent inbound message ids retained for at-least-once de-dup (iLink has no delivery guarantee stated). */
|
|
106
|
+
const RECENT_MESSAGE_CACHE_SIZE = 200;
|
|
107
|
+
const DEFAULT_TIMING = {
|
|
108
|
+
pollTimeoutSeconds: POLL_TIMEOUT_SECONDS,
|
|
109
|
+
pollRetryDelayMs: POLL_RETRY_DELAY_MS,
|
|
110
|
+
pollBackoffDelayMs: POLL_BACKOFF_DELAY_MS,
|
|
111
|
+
pollMaxConsecutiveFailures: POLL_MAX_CONSECUTIVE_FAILURES,
|
|
112
|
+
linkAttemptTimeoutMs: LINK_ATTEMPT_TIMEOUT_MS,
|
|
113
|
+
linkPollIntervalMs: LINK_POLL_INTERVAL_MS,
|
|
114
|
+
pollIdleDelayMs: 0,
|
|
115
|
+
};
|
|
116
|
+
/** Split outbound text at iLink's documented 4000-char limit, on whole lines where possible. */
|
|
117
|
+
function chunkWeChatText(text) {
|
|
118
|
+
if (text.length <= exports.WECHAT_MAX_MESSAGE_LENGTH)
|
|
119
|
+
return [text];
|
|
120
|
+
const chunks = [];
|
|
121
|
+
let rest = text;
|
|
122
|
+
while (rest.length > exports.WECHAT_MAX_MESSAGE_LENGTH) {
|
|
123
|
+
let cut = rest.lastIndexOf('\n', exports.WECHAT_MAX_MESSAGE_LENGTH);
|
|
124
|
+
if (cut <= 0)
|
|
125
|
+
cut = exports.WECHAT_MAX_MESSAGE_LENGTH;
|
|
126
|
+
chunks.push(rest.slice(0, cut));
|
|
127
|
+
rest = rest.slice(cut).replace(/^\n/, '');
|
|
128
|
+
}
|
|
129
|
+
if (rest.length > 0)
|
|
130
|
+
chunks.push(rest);
|
|
131
|
+
return chunks;
|
|
132
|
+
}
|
|
133
|
+
function isWeChatChannelEnabled() {
|
|
134
|
+
return process.env.WECHAT_CHANNEL_DISABLED !== 'true';
|
|
135
|
+
}
|
|
136
|
+
function wechatStateFile(workspace) {
|
|
137
|
+
return path.join(workspace, exports.WECHAT_STATE_DIR, 'session.json');
|
|
138
|
+
}
|
|
139
|
+
class WeChatManager {
|
|
140
|
+
constructor(agentConfig, logDir, client = (0, ilink_client_1.createILinkClient)('', agentConfig.wechat?.botAgent),
|
|
141
|
+
/** Called once per new inbound message, after de-dup — never for a retried delivery. */
|
|
142
|
+
onMessage, timing = DEFAULT_TIMING) {
|
|
143
|
+
this.agentConfig = agentConfig;
|
|
144
|
+
this.client = client;
|
|
145
|
+
this.onMessage = onMessage;
|
|
146
|
+
this.timing = timing;
|
|
147
|
+
this.status = 'unlinked';
|
|
148
|
+
this.loggedOut = false;
|
|
149
|
+
this.stopping = false;
|
|
150
|
+
this.contextTokens = {};
|
|
151
|
+
this.recentMessageIds = new Set();
|
|
152
|
+
this.recentMessageOrder = [];
|
|
153
|
+
this.pollGeneration = 0;
|
|
154
|
+
this.stateFile = wechatStateFile(agentConfig.workspace);
|
|
155
|
+
this.logger = (0, logger_1.createLogger)(`${agentConfig.id}:wechat`, logDir);
|
|
156
|
+
}
|
|
157
|
+
updateAgentConfig(newConfig) {
|
|
158
|
+
this.agentConfig = newConfig;
|
|
159
|
+
}
|
|
160
|
+
getStatus() {
|
|
161
|
+
return { status: this.status, qr: this.qrDataUri, loggedOut: this.loggedOut };
|
|
162
|
+
}
|
|
163
|
+
/** Resume a previously-linked session on gateway boot — no-op if never linked. */
|
|
164
|
+
async resumeIfLinked() {
|
|
165
|
+
if (!isWeChatChannelEnabled())
|
|
166
|
+
return;
|
|
167
|
+
const saved = await this.readSession();
|
|
168
|
+
if (!saved)
|
|
169
|
+
return;
|
|
170
|
+
this.credentials = saved.credentials;
|
|
171
|
+
this.contextTokens = saved.contextTokens;
|
|
172
|
+
this.status = 'linked';
|
|
173
|
+
this.logger.info('Resuming previously-linked WeChat session', { agentId: this.agentConfig.id });
|
|
174
|
+
this.startPollLoop();
|
|
175
|
+
}
|
|
176
|
+
/**
|
|
177
|
+
* Start a fresh QR-code linking flow. Blocked only if an admin has set
|
|
178
|
+
* `WECHAT_CHANNEL_DISABLED` — the hard kill switch for a third-party
|
|
179
|
+
* dependency no deployer of this gateway controls (see module doc comment).
|
|
180
|
+
*/
|
|
181
|
+
async startLinking() {
|
|
182
|
+
if (!isWeChatChannelEnabled()) {
|
|
183
|
+
throw new Error('WeChat channel is disabled (WECHAT_CHANNEL_DISABLED is "true") — the iLink bridge ' +
|
|
184
|
+
'this channel depends on can be killed instantly without a redeploy; ask an admin to re-enable it.');
|
|
185
|
+
}
|
|
186
|
+
this.stopping = false;
|
|
187
|
+
this.loggedOut = false;
|
|
188
|
+
const session = await this.client.requestLinkQr();
|
|
189
|
+
this.qrDataUri = session.qrDataUri;
|
|
190
|
+
this.status = 'pending_scan';
|
|
191
|
+
const deadline = Date.now() + this.timing.linkAttemptTimeoutMs;
|
|
192
|
+
let lastLoggedStatus;
|
|
193
|
+
while (!this.stopping && Date.now() < deadline) {
|
|
194
|
+
await sleep(this.timing.linkPollIntervalMs);
|
|
195
|
+
let result;
|
|
196
|
+
try {
|
|
197
|
+
result = await this.client.pollLinkStatus(session.loginSessionId);
|
|
198
|
+
}
|
|
199
|
+
catch (err) {
|
|
200
|
+
// A single request failing/timing out (observed live: the host
|
|
201
|
+
// `scaned_but_redirect` redirects to can be slow or unresponsive)
|
|
202
|
+
// must not abort the whole attempt — keep polling until the
|
|
203
|
+
// deadline above, same as a transient "wait" status would.
|
|
204
|
+
this.logger.warn('WeChat QR status poll failed, retrying', {
|
|
205
|
+
agentId: this.agentConfig.id,
|
|
206
|
+
error: err.message,
|
|
207
|
+
});
|
|
208
|
+
continue;
|
|
209
|
+
}
|
|
210
|
+
// Only every STATUS CHANGE is logged (not every poll) — a real attempt
|
|
211
|
+
// polls every 2s for up to 2 minutes, so logging unconditionally would
|
|
212
|
+
// mostly just repeat "wait" dozens of times.
|
|
213
|
+
if (result.status && result.status !== lastLoggedStatus) {
|
|
214
|
+
this.logger.info('WeChat QR link status changed', {
|
|
215
|
+
agentId: this.agentConfig.id,
|
|
216
|
+
status: result.status,
|
|
217
|
+
});
|
|
218
|
+
lastLoggedStatus = result.status;
|
|
219
|
+
}
|
|
220
|
+
if (result.linked && result.credentials) {
|
|
221
|
+
this.credentials = result.credentials;
|
|
222
|
+
this.contextTokens = {};
|
|
223
|
+
this.qrDataUri = undefined;
|
|
224
|
+
this.status = 'linked';
|
|
225
|
+
await this.persistSession();
|
|
226
|
+
this.startPollLoop();
|
|
227
|
+
return;
|
|
228
|
+
}
|
|
229
|
+
}
|
|
230
|
+
if (!this.stopping) {
|
|
231
|
+
this.logger.warn('WeChat QR link attempt timed out', {
|
|
232
|
+
agentId: this.agentConfig.id,
|
|
233
|
+
lastStatus: lastLoggedStatus ?? 'unknown',
|
|
234
|
+
});
|
|
235
|
+
this.status = 'unlinked';
|
|
236
|
+
this.qrDataUri = undefined;
|
|
237
|
+
}
|
|
238
|
+
}
|
|
239
|
+
/** Logout and wipe the linked session. The user must scan fresh afterward. */
|
|
240
|
+
async unlink() {
|
|
241
|
+
this.stopping = true;
|
|
242
|
+
this.pollGeneration += 1; // orphans any in-flight poll loop's iteration check
|
|
243
|
+
await this.pollLoopPromise?.catch(() => { });
|
|
244
|
+
if (this.credentials) {
|
|
245
|
+
await this.client.notifyStop(this.credentials).catch((err) => {
|
|
246
|
+
this.logger.warn('WeChat notifyStop failed (continuing anyway)', {
|
|
247
|
+
agentId: this.agentConfig.id,
|
|
248
|
+
error: err.message,
|
|
249
|
+
});
|
|
250
|
+
});
|
|
251
|
+
}
|
|
252
|
+
this.credentials = undefined;
|
|
253
|
+
this.contextTokens = {};
|
|
254
|
+
this.qrDataUri = undefined;
|
|
255
|
+
this.status = 'unlinked';
|
|
256
|
+
this.loggedOut = false;
|
|
257
|
+
await fsp.rm(this.stateFile, { force: true }).catch(() => { });
|
|
258
|
+
}
|
|
259
|
+
/**
|
|
260
|
+
* Send a single outbound message, chunked over iLink's 4000-char limit with
|
|
261
|
+
* the documented 0.3s inter-chunk delay. Media is out of scope for v1 (see
|
|
262
|
+
* the plan's non-goals) — text only.
|
|
263
|
+
*
|
|
264
|
+
* `contextToken` is NOT refreshed here — per Tencent's real protocol
|
|
265
|
+
* (confirmed against `Tencent/openclaw-weixin`'s own doc), the token flows
|
|
266
|
+
* the other way: an INBOUND message establishes it (captured in
|
|
267
|
+
* `runPollLoop` below), and every subsequent send to that sender echoes
|
|
268
|
+
* whatever was captured last. `sendmessage`'s own response carries no
|
|
269
|
+
* token to update.
|
|
270
|
+
*/
|
|
271
|
+
async sendMessage(toId, text) {
|
|
272
|
+
if (!isWeChatChannelEnabled()) {
|
|
273
|
+
throw new Error('WeChat channel is disabled (WECHAT_CHANNEL_DISABLED is "true") — the iLink bridge ' +
|
|
274
|
+
'this channel depends on can be killed instantly without a redeploy; ask an admin to re-enable it.');
|
|
275
|
+
}
|
|
276
|
+
if (!this.credentials)
|
|
277
|
+
throw new Error('WeChat account is not linked');
|
|
278
|
+
const chunks = chunkWeChatText(text);
|
|
279
|
+
for (let i = 0; i < chunks.length; i++) {
|
|
280
|
+
await this.client.sendText(this.credentials, toId, chunks[i], this.contextTokens[toId]);
|
|
281
|
+
if (i < chunks.length - 1)
|
|
282
|
+
await sleep(exports.WECHAT_CHUNK_DELAY_MS);
|
|
283
|
+
}
|
|
284
|
+
await this.persistSession();
|
|
285
|
+
}
|
|
286
|
+
startPollLoop() {
|
|
287
|
+
const generation = ++this.pollGeneration;
|
|
288
|
+
this.pollLoopPromise = this.runPollLoop(generation);
|
|
289
|
+
}
|
|
290
|
+
async runPollLoop(generation) {
|
|
291
|
+
// Tell iLink this client is now listening, before the first getUpdates
|
|
292
|
+
// call — see ILinkClient.notifyStart's doc comment. Mirrors Tencent's
|
|
293
|
+
// own client exactly: never blocks startup on failure, just logs.
|
|
294
|
+
if (this.credentials) {
|
|
295
|
+
try {
|
|
296
|
+
await this.client.notifyStart(this.credentials);
|
|
297
|
+
}
|
|
298
|
+
catch (err) {
|
|
299
|
+
this.logger.warn('WeChat notifyStart failed (continuing anyway)', {
|
|
300
|
+
agentId: this.agentConfig.id,
|
|
301
|
+
error: err.message,
|
|
302
|
+
});
|
|
303
|
+
}
|
|
304
|
+
}
|
|
305
|
+
let consecutiveFailures = 0;
|
|
306
|
+
while (!this.stopping && generation === this.pollGeneration && this.credentials) {
|
|
307
|
+
if (!isWeChatChannelEnabled()) {
|
|
308
|
+
// Admin flipped the kill switch while this loop was already running
|
|
309
|
+
// (resumeIfLinked()/startLinking() only check it before the loop
|
|
310
|
+
// starts) — stop dispatching on the next iteration boundary rather
|
|
311
|
+
// than requiring a redeploy/restart to take effect.
|
|
312
|
+
this.logger.warn('WeChat channel disabled mid-run, stopping poll loop', {
|
|
313
|
+
agentId: this.agentConfig.id,
|
|
314
|
+
});
|
|
315
|
+
return;
|
|
316
|
+
}
|
|
317
|
+
try {
|
|
318
|
+
const updates = await this.client.getUpdates(this.credentials, this.timing.pollTimeoutSeconds);
|
|
319
|
+
consecutiveFailures = 0;
|
|
320
|
+
for (const update of updates) {
|
|
321
|
+
// Captured unconditionally, even for a redelivered id: iLink may
|
|
322
|
+
// hand back a fresher token on a retry, and there's no separate
|
|
323
|
+
// signal for "this token changed" to key off instead.
|
|
324
|
+
if (update.contextToken)
|
|
325
|
+
this.contextTokens[update.fromId] = update.contextToken;
|
|
326
|
+
if (this.isDuplicate(update.id))
|
|
327
|
+
continue;
|
|
328
|
+
this.rememberMessage(update.id);
|
|
329
|
+
this.onMessage?.(update);
|
|
330
|
+
}
|
|
331
|
+
if (this.timing.pollIdleDelayMs > 0)
|
|
332
|
+
await sleep(this.timing.pollIdleDelayMs);
|
|
333
|
+
}
|
|
334
|
+
catch (err) {
|
|
335
|
+
consecutiveFailures += 1;
|
|
336
|
+
// Flat 2s retry for the first few failures, one fixed 30s pause after
|
|
337
|
+
// pollMaxConsecutiveFailures in a row, then reset — NOT exponential
|
|
338
|
+
// backoff. See POLL_RETRY_DELAY_MS's doc comment for why.
|
|
339
|
+
const backingOff = consecutiveFailures >= this.timing.pollMaxConsecutiveFailures;
|
|
340
|
+
this.logger.warn('WeChat getUpdates failed, retrying', {
|
|
341
|
+
agentId: this.agentConfig.id,
|
|
342
|
+
error: err.message,
|
|
343
|
+
consecutiveFailures,
|
|
344
|
+
backingOff,
|
|
345
|
+
});
|
|
346
|
+
// Deliberately NOT flipping to 'reconnecting' here, at any failure
|
|
347
|
+
// count. Unlike WhatsApp/Baileys' persistent socket (where a drop is
|
|
348
|
+
// real and 'reconnecting' means something), getUpdates is a
|
|
349
|
+
// stateless long-poll retried in a loop — a thrown error here is
|
|
350
|
+
// almost always just a Cloudflare edge timeout on an otherwise-idle
|
|
351
|
+
// poll (confirmed live: happens on the large majority of idle polls
|
|
352
|
+
// against a perfectly healthy, still-linked account), not a session
|
|
353
|
+
// problem. Marking 'reconnecting' — which the web UI reads as
|
|
354
|
+
// wechat_connected=false and hides the pending-senders/allowlist
|
|
355
|
+
// section for — on ordinary transport errors made the UI flap
|
|
356
|
+
// between connected/disconnected during completely normal idle
|
|
357
|
+
// operation. `status` stays 'linked' through routine getUpdates
|
|
358
|
+
// failures; only a real session problem (not detected yet — would
|
|
359
|
+
// need iLink's business-level ret/errcode, which the thrown Error
|
|
360
|
+
// here doesn't carry structured) should ever downgrade it.
|
|
361
|
+
await sleep(backingOff ? this.timing.pollBackoffDelayMs : this.timing.pollRetryDelayMs);
|
|
362
|
+
if (backingOff)
|
|
363
|
+
consecutiveFailures = 0;
|
|
364
|
+
continue;
|
|
365
|
+
}
|
|
366
|
+
if (this.status === 'reconnecting')
|
|
367
|
+
this.status = 'linked';
|
|
368
|
+
}
|
|
369
|
+
}
|
|
370
|
+
isDuplicate(id) {
|
|
371
|
+
return this.recentMessageIds.has(id);
|
|
372
|
+
}
|
|
373
|
+
rememberMessage(id) {
|
|
374
|
+
this.recentMessageIds.add(id);
|
|
375
|
+
this.recentMessageOrder.push(id);
|
|
376
|
+
if (this.recentMessageOrder.length > RECENT_MESSAGE_CACHE_SIZE) {
|
|
377
|
+
const oldest = this.recentMessageOrder.shift();
|
|
378
|
+
if (oldest !== undefined)
|
|
379
|
+
this.recentMessageIds.delete(oldest);
|
|
380
|
+
}
|
|
381
|
+
}
|
|
382
|
+
async readSession() {
|
|
383
|
+
try {
|
|
384
|
+
const raw = await fsp.readFile(this.stateFile, 'utf-8');
|
|
385
|
+
return JSON.parse(raw);
|
|
386
|
+
}
|
|
387
|
+
catch {
|
|
388
|
+
return undefined;
|
|
389
|
+
}
|
|
390
|
+
}
|
|
391
|
+
async persistSession() {
|
|
392
|
+
if (!this.credentials)
|
|
393
|
+
return;
|
|
394
|
+
const dir = path.dirname(this.stateFile);
|
|
395
|
+
await fsp.mkdir(dir, { recursive: true, mode: 0o700 });
|
|
396
|
+
const payload = { credentials: this.credentials, contextTokens: this.contextTokens };
|
|
397
|
+
await fsp.writeFile(this.stateFile, JSON.stringify(payload), { mode: 0o600 });
|
|
398
|
+
}
|
|
399
|
+
}
|
|
400
|
+
exports.WeChatManager = WeChatManager;
|
|
401
|
+
function sleep(ms) {
|
|
402
|
+
return new Promise((resolve) => setTimeout(resolve, ms));
|
|
403
|
+
}
|
|
404
|
+
// Re-exported so callers (router/runner) don't need to import fs directly
|
|
405
|
+
// just to check whether a session file exists before constructing a manager.
|
|
406
|
+
function hasSavedWeChatSession(workspace) {
|
|
407
|
+
return fs.existsSync(wechatStateFile(workspace));
|
|
408
|
+
}
|
|
409
|
+
//# sourceMappingURL=manager.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"manager.js","sourceRoot":"","sources":["../../src/wechat/manager.ts"],"names":[],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;AA0HA,0CAYC;AAED,wDAEC;AAiSD,sDAEC;AA7aD;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GA+BG;AACH,uCAAyB;AACzB,iDAAmC;AACnC,2CAA6B;AAE7B,sCAAyC;AACzC,iDAKwB;AAYxB,+FAA+F;AAClF,QAAA,gBAAgB,GAAG,eAAe,CAAC;AAEhD,yEAAyE;AAC5D,QAAA,yBAAyB,GAAG,IAAI,CAAC;AAE9C,iFAAiF;AACpE,QAAA,qBAAqB,GAAG,GAAG,CAAC;AAEzC,wFAAwF;AACxF,MAAM,oBAAoB,GAAG,EAAE,CAAC;AAEhC;;;;;;;;;;;;;GAaG;AACH,MAAM,mBAAmB,GAAG,IAAK,CAAC;AAClC,MAAM,qBAAqB,GAAG,KAAM,CAAC;AACrC,MAAM,6BAA6B,GAAG,CAAC,CAAC;AAExC,4FAA4F;AAC5F,MAAM,uBAAuB,GAAG,CAAC,GAAG,EAAE,GAAG,IAAI,CAAC;AAC9C,MAAM,qBAAqB,GAAG,IAAK,CAAC;AAEpC,6GAA6G;AAC7G,MAAM,yBAAyB,GAAG,GAAG,CAAC;AAsBtC,MAAM,cAAc,GAAwB;IAC1C,kBAAkB,EAAE,oBAAoB;IACxC,gBAAgB,EAAE,mBAAmB;IACrC,kBAAkB,EAAE,qBAAqB;IACzC,0BAA0B,EAAE,6BAA6B;IACzD,oBAAoB,EAAE,uBAAuB;IAC7C,kBAAkB,EAAE,qBAAqB;IACzC,eAAe,EAAE,CAAC;CACnB,CAAC;AAEF,gGAAgG;AAChG,SAAgB,eAAe,CAAC,IAAY;IAC1C,IAAI,IAAI,CAAC,MAAM,IAAI,iCAAyB;QAAE,OAAO,CAAC,IAAI,CAAC,CAAC;IAC5D,MAAM,MAAM,GAAa,EAAE,CAAC;IAC5B,IAAI,IAAI,GAAG,IAAI,CAAC;IAChB,OAAO,IAAI,CAAC,MAAM,GAAG,iCAAyB,EAAE,CAAC;QAC/C,IAAI,GAAG,GAAG,IAAI,CAAC,WAAW,CAAC,IAAI,EAAE,iCAAyB,CAAC,CAAC;QAC5D,IAAI,GAAG,IAAI,CAAC;YAAE,GAAG,GAAG,iCAAyB,CAAC;QAC9C,MAAM,CAAC,IAAI,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC,EAAE,GAAG,CAAC,CAAC,CAAC;QAChC,IAAI,GAAG,IAAI,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC,OAAO,CAAC,KAAK,EAAE,EAAE,CAAC,CAAC;IAC5C,CAAC;IACD,IAAI,IAAI,CAAC,MAAM,GAAG,CAAC;QAAE,MAAM,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;IACvC,OAAO,MAAM,CAAC;AAChB,CAAC;AAED,SAAgB,sBAAsB;IACpC,OAAO,OAAO,CAAC,GAAG,CAAC,uBAAuB,KAAK,MAAM,CAAC;AACxD,CAAC;AAED,SAAS,eAAe,CAAC,SAAiB;IACxC,OAAO,IAAI,CAAC,IAAI,CAAC,SAAS,EAAE,wBAAgB,EAAE,cAAc,CAAC,CAAC;AAChE,CAAC;AAQD,MAAa,aAAa;IAcxB,YACU,WAAwB,EAChC,MAAc,EACG,SAAsB,IAAA,gCAAiB,EAAC,EAAE,EAAE,WAAW,CAAC,MAAM,EAAE,QAAQ,CAAC;IAC1F,wFAAwF;IACvE,SAAyC,EACzC,SAA8B,cAAc;QALrD,gBAAW,GAAX,WAAW,CAAa;QAEf,WAAM,GAAN,MAAM,CAAmE;QAEzE,cAAS,GAAT,SAAS,CAAgC;QACzC,WAAM,GAAN,MAAM,CAAsC;QAnBvD,WAAM,GAAqB,UAAU,CAAC;QAEtC,cAAS,GAAG,KAAK,CAAC;QAClB,aAAQ,GAAG,KAAK,CAAC;QAEjB,kBAAa,GAA2B,EAAE,CAAC;QAGlC,qBAAgB,GAAG,IAAI,GAAG,EAAU,CAAC;QACrC,uBAAkB,GAAa,EAAE,CAAC;QAE3C,mBAAc,GAAG,CAAC,CAAC;QAUzB,IAAI,CAAC,SAAS,GAAG,eAAe,CAAC,WAAW,CAAC,SAAS,CAAC,CAAC;QACxD,IAAI,CAAC,MAAM,GAAG,IAAA,qBAAY,EAAC,GAAG,WAAW,CAAC,EAAE,SAAS,EAAE,MAAM,CAAC,CAAC;IACjE,CAAC;IAED,iBAAiB,CAAC,SAAsB;QACtC,IAAI,CAAC,WAAW,GAAG,SAAS,CAAC;IAC/B,CAAC;IAED,SAAS;QACP,OAAO,EAAE,MAAM,EAAE,IAAI,CAAC,MAAM,EAAE,EAAE,EAAE,IAAI,CAAC,SAAS,EAAE,SAAS,EAAE,IAAI,CAAC,SAAS,EAAE,CAAC;IAChF,CAAC;IAED,kFAAkF;IAClF,KAAK,CAAC,cAAc;QAClB,IAAI,CAAC,sBAAsB,EAAE;YAAE,OAAO;QACtC,MAAM,KAAK,GAAG,MAAM,IAAI,CAAC,WAAW,EAAE,CAAC;QACvC,IAAI,CAAC,KAAK;YAAE,OAAO;QACnB,IAAI,CAAC,WAAW,GAAG,KAAK,CAAC,WAAW,CAAC;QACrC,IAAI,CAAC,aAAa,GAAG,KAAK,CAAC,aAAa,CAAC;QACzC,IAAI,CAAC,MAAM,GAAG,QAAQ,CAAC;QACvB,IAAI,CAAC,MAAM,CAAC,IAAI,CAAC,2CAA2C,EAAE,EAAE,OAAO,EAAE,IAAI,CAAC,WAAW,CAAC,EAAE,EAAE,CAAC,CAAC;QAChG,IAAI,CAAC,aAAa,EAAE,CAAC;IACvB,CAAC;IAED;;;;OAIG;IACH,KAAK,CAAC,YAAY;QAChB,IAAI,CAAC,sBAAsB,EAAE,EAAE,CAAC;YAC9B,MAAM,IAAI,KAAK,CACb,oFAAoF;gBAClF,mGAAmG,CACtG,CAAC;QACJ,CAAC;QACD,IAAI,CAAC,QAAQ,GAAG,KAAK,CAAC;QACtB,IAAI,CAAC,SAAS,GAAG,KAAK,CAAC;QACvB,MAAM,OAAO,GAAG,MAAM,IAAI,CAAC,MAAM,CAAC,aAAa,EAAE,CAAC;QAClD,IAAI,CAAC,SAAS,GAAG,OAAO,CAAC,SAAS,CAAC;QACnC,IAAI,CAAC,MAAM,GAAG,cAAc,CAAC;QAE7B,MAAM,QAAQ,GAAG,IAAI,CAAC,GAAG,EAAE,GAAG,IAAI,CAAC,MAAM,CAAC,oBAAoB,CAAC;QAC/D,IAAI,gBAAoC,CAAC;QACzC,OAAO,CAAC,IAAI,CAAC,QAAQ,IAAI,IAAI,CAAC,GAAG,EAAE,GAAG,QAAQ,EAAE,CAAC;YAC/C,MAAM,KAAK,CAAC,IAAI,CAAC,MAAM,CAAC,kBAAkB,CAAC,CAAC;YAC5C,IAAI,MAAM,CAAC;YACX,IAAI,CAAC;gBACH,MAAM,GAAG,MAAM,IAAI,CAAC,MAAM,CAAC,cAAc,CAAC,OAAO,CAAC,cAAc,CAAC,CAAC;YACpE,CAAC;YAAC,OAAO,GAAG,EAAE,CAAC;gBACb,+DAA+D;gBAC/D,kEAAkE;gBAClE,4DAA4D;gBAC5D,2DAA2D;gBAC3D,IAAI,CAAC,MAAM,CAAC,IAAI,CAAC,wCAAwC,EAAE;oBACzD,OAAO,EAAE,IAAI,CAAC,WAAW,CAAC,EAAE;oBAC5B,KAAK,EAAG,GAAa,CAAC,OAAO;iBAC9B,CAAC,CAAC;gBACH,SAAS;YACX,CAAC;YACD,uEAAuE;YACvE,uEAAuE;YACvE,6CAA6C;YAC7C,IAAI,MAAM,CAAC,MAAM,IAAI,MAAM,CAAC,MAAM,KAAK,gBAAgB,EAAE,CAAC;gBACxD,IAAI,CAAC,MAAM,CAAC,IAAI,CAAC,+BAA+B,EAAE;oBAChD,OAAO,EAAE,IAAI,CAAC,WAAW,CAAC,EAAE;oBAC5B,MAAM,EAAE,MAAM,CAAC,MAAM;iBACtB,CAAC,CAAC;gBACH,gBAAgB,GAAG,MAAM,CAAC,MAAM,CAAC;YACnC,CAAC;YACD,IAAI,MAAM,CAAC,MAAM,IAAI,MAAM,CAAC,WAAW,EAAE,CAAC;gBACxC,IAAI,CAAC,WAAW,GAAG,MAAM,CAAC,WAAW,CAAC;gBACtC,IAAI,CAAC,aAAa,GAAG,EAAE,CAAC;gBACxB,IAAI,CAAC,SAAS,GAAG,SAAS,CAAC;gBAC3B,IAAI,CAAC,MAAM,GAAG,QAAQ,CAAC;gBACvB,MAAM,IAAI,CAAC,cAAc,EAAE,CAAC;gBAC5B,IAAI,CAAC,aAAa,EAAE,CAAC;gBACrB,OAAO;YACT,CAAC;QACH,CAAC;QACD,IAAI,CAAC,IAAI,CAAC,QAAQ,EAAE,CAAC;YACnB,IAAI,CAAC,MAAM,CAAC,IAAI,CAAC,kCAAkC,EAAE;gBACnD,OAAO,EAAE,IAAI,CAAC,WAAW,CAAC,EAAE;gBAC5B,UAAU,EAAE,gBAAgB,IAAI,SAAS;aAC1C,CAAC,CAAC;YACH,IAAI,CAAC,MAAM,GAAG,UAAU,CAAC;YACzB,IAAI,CAAC,SAAS,GAAG,SAAS,CAAC;QAC7B,CAAC;IACH,CAAC;IAED,8EAA8E;IAC9E,KAAK,CAAC,MAAM;QACV,IAAI,CAAC,QAAQ,GAAG,IAAI,CAAC;QACrB,IAAI,CAAC,cAAc,IAAI,CAAC,CAAC,CAAC,oDAAoD;QAC9E,MAAM,IAAI,CAAC,eAAe,EAAE,KAAK,CAAC,GAAG,EAAE,GAAE,CAAC,CAAC,CAAC;QAC5C,IAAI,IAAI,CAAC,WAAW,EAAE,CAAC;YACrB,MAAM,IAAI,CAAC,MAAM,CAAC,UAAU,CAAC,IAAI,CAAC,WAAW,CAAC,CAAC,KAAK,CAAC,CAAC,GAAG,EAAE,EAAE;gBAC3D,IAAI,CAAC,MAAM,CAAC,IAAI,CAAC,8CAA8C,EAAE;oBAC/D,OAAO,EAAE,IAAI,CAAC,WAAW,CAAC,EAAE;oBAC5B,KAAK,EAAG,GAAa,CAAC,OAAO;iBAC9B,CAAC,CAAC;YACL,CAAC,CAAC,CAAC;QACL,CAAC;QACD,IAAI,CAAC,WAAW,GAAG,SAAS,CAAC;QAC7B,IAAI,CAAC,aAAa,GAAG,EAAE,CAAC;QACxB,IAAI,CAAC,SAAS,GAAG,SAAS,CAAC;QAC3B,IAAI,CAAC,MAAM,GAAG,UAAU,CAAC;QACzB,IAAI,CAAC,SAAS,GAAG,KAAK,CAAC;QACvB,MAAM,GAAG,CAAC,EAAE,CAAC,IAAI,CAAC,SAAS,EAAE,EAAE,KAAK,EAAE,IAAI,EAAE,CAAC,CAAC,KAAK,CAAC,GAAG,EAAE,GAAE,CAAC,CAAC,CAAC;IAChE,CAAC;IAED;;;;;;;;;;;OAWG;IACH,KAAK,CAAC,WAAW,CAAC,IAAY,EAAE,IAAY;QAC1C,IAAI,CAAC,sBAAsB,EAAE,EAAE,CAAC;YAC9B,MAAM,IAAI,KAAK,CACb,oFAAoF;gBAClF,mGAAmG,CACtG,CAAC;QACJ,CAAC;QACD,IAAI,CAAC,IAAI,CAAC,WAAW;YAAE,MAAM,IAAI,KAAK,CAAC,8BAA8B,CAAC,CAAC;QACvE,MAAM,MAAM,GAAG,eAAe,CAAC,IAAI,CAAC,CAAC;QACrC,KAAK,IAAI,CAAC,GAAG,CAAC,EAAE,CAAC,GAAG,MAAM,CAAC,MAAM,EAAE,CAAC,EAAE,EAAE,CAAC;YACvC,MAAM,IAAI,CAAC,MAAM,CAAC,QAAQ,CAAC,IAAI,CAAC,WAAW,EAAE,IAAI,EAAE,MAAM,CAAC,CAAC,CAAC,EAAE,IAAI,CAAC,aAAa,CAAC,IAAI,CAAC,CAAC,CAAC;YACxF,IAAI,CAAC,GAAG,MAAM,CAAC,MAAM,GAAG,CAAC;gBAAE,MAAM,KAAK,CAAC,6BAAqB,CAAC,CAAC;QAChE,CAAC;QACD,MAAM,IAAI,CAAC,cAAc,EAAE,CAAC;IAC9B,CAAC;IAEO,aAAa;QACnB,MAAM,UAAU,GAAG,EAAE,IAAI,CAAC,cAAc,CAAC;QACzC,IAAI,CAAC,eAAe,GAAG,IAAI,CAAC,WAAW,CAAC,UAAU,CAAC,CAAC;IACtD,CAAC;IAEO,KAAK,CAAC,WAAW,CAAC,UAAkB;QAC1C,uEAAuE;QACvE,sEAAsE;QACtE,kEAAkE;QAClE,IAAI,IAAI,CAAC,WAAW,EAAE,CAAC;YACrB,IAAI,CAAC;gBACH,MAAM,IAAI,CAAC,MAAM,CAAC,WAAW,CAAC,IAAI,CAAC,WAAW,CAAC,CAAC;YAClD,CAAC;YAAC,OAAO,GAAG,EAAE,CAAC;gBACb,IAAI,CAAC,MAAM,CAAC,IAAI,CAAC,+CAA+C,EAAE;oBAChE,OAAO,EAAE,IAAI,CAAC,WAAW,CAAC,EAAE;oBAC5B,KAAK,EAAG,GAAa,CAAC,OAAO;iBAC9B,CAAC,CAAC;YACL,CAAC;QACH,CAAC;QACD,IAAI,mBAAmB,GAAG,CAAC,CAAC;QAC5B,OAAO,CAAC,IAAI,CAAC,QAAQ,IAAI,UAAU,KAAK,IAAI,CAAC,cAAc,IAAI,IAAI,CAAC,WAAW,EAAE,CAAC;YAChF,IAAI,CAAC,sBAAsB,EAAE,EAAE,CAAC;gBAC9B,oEAAoE;gBACpE,iEAAiE;gBACjE,mEAAmE;gBACnE,oDAAoD;gBACpD,IAAI,CAAC,MAAM,CAAC,IAAI,CAAC,qDAAqD,EAAE;oBACtE,OAAO,EAAE,IAAI,CAAC,WAAW,CAAC,EAAE;iBAC7B,CAAC,CAAC;gBACH,OAAO;YACT,CAAC;YACD,IAAI,CAAC;gBACH,MAAM,OAAO,GAAG,MAAM,IAAI,CAAC,MAAM,CAAC,UAAU,CAAC,IAAI,CAAC,WAAW,EAAE,IAAI,CAAC,MAAM,CAAC,kBAAkB,CAAC,CAAC;gBAC/F,mBAAmB,GAAG,CAAC,CAAC;gBACxB,KAAK,MAAM,MAAM,IAAI,OAAO,EAAE,CAAC;oBAC7B,iEAAiE;oBACjE,gEAAgE;oBAChE,sDAAsD;oBACtD,IAAI,MAAM,CAAC,YAAY;wBAAE,IAAI,CAAC,aAAa,CAAC,MAAM,CAAC,MAAM,CAAC,GAAG,MAAM,CAAC,YAAY,CAAC;oBACjF,IAAI,IAAI,CAAC,WAAW,CAAC,MAAM,CAAC,EAAE,CAAC;wBAAE,SAAS;oBAC1C,IAAI,CAAC,eAAe,CAAC,MAAM,CAAC,EAAE,CAAC,CAAC;oBAChC,IAAI,CAAC,SAAS,EAAE,CAAC,MAAM,CAAC,CAAC;gBAC3B,CAAC;gBACD,IAAI,IAAI,CAAC,MAAM,CAAC,eAAe,GAAG,CAAC;oBAAE,MAAM,KAAK,CAAC,IAAI,CAAC,MAAM,CAAC,eAAe,CAAC,CAAC;YAChF,CAAC;YAAC,OAAO,GAAG,EAAE,CAAC;gBACb,mBAAmB,IAAI,CAAC,CAAC;gBACzB,sEAAsE;gBACtE,oEAAoE;gBACpE,0DAA0D;gBAC1D,MAAM,UAAU,GAAG,mBAAmB,IAAI,IAAI,CAAC,MAAM,CAAC,0BAA0B,CAAC;gBACjF,IAAI,CAAC,MAAM,CAAC,IAAI,CAAC,oCAAoC,EAAE;oBACrD,OAAO,EAAE,IAAI,CAAC,WAAW,CAAC,EAAE;oBAC5B,KAAK,EAAG,GAAa,CAAC,OAAO;oBAC7B,mBAAmB;oBACnB,UAAU;iBACX,CAAC,CAAC;gBACH,mEAAmE;gBACnE,qEAAqE;gBACrE,4DAA4D;gBAC5D,iEAAiE;gBACjE,oEAAoE;gBACpE,oEAAoE;gBACpE,oEAAoE;gBACpE,8DAA8D;gBAC9D,iEAAiE;gBACjE,8DAA8D;gBAC9D,+DAA+D;gBAC/D,gEAAgE;gBAChE,kEAAkE;gBAClE,kEAAkE;gBAClE,2DAA2D;gBAC3D,MAAM,KAAK,CAAC,UAAU,CAAC,CAAC,CAAC,IAAI,CAAC,MAAM,CAAC,kBAAkB,CAAC,CAAC,CAAC,IAAI,CAAC,MAAM,CAAC,gBAAgB,CAAC,CAAC;gBACxF,IAAI,UAAU;oBAAE,mBAAmB,GAAG,CAAC,CAAC;gBACxC,SAAS;YACX,CAAC;YACD,IAAI,IAAI,CAAC,MAAM,KAAK,cAAc;gBAAE,IAAI,CAAC,MAAM,GAAG,QAAQ,CAAC;QAC7D,CAAC;IACH,CAAC;IAEO,WAAW,CAAC,EAAU;QAC5B,OAAO,IAAI,CAAC,gBAAgB,CAAC,GAAG,CAAC,EAAE,CAAC,CAAC;IACvC,CAAC;IAEO,eAAe,CAAC,EAAU;QAChC,IAAI,CAAC,gBAAgB,CAAC,GAAG,CAAC,EAAE,CAAC,CAAC;QAC9B,IAAI,CAAC,kBAAkB,CAAC,IAAI,CAAC,EAAE,CAAC,CAAC;QACjC,IAAI,IAAI,CAAC,kBAAkB,CAAC,MAAM,GAAG,yBAAyB,EAAE,CAAC;YAC/D,MAAM,MAAM,GAAG,IAAI,CAAC,kBAAkB,CAAC,KAAK,EAAE,CAAC;YAC/C,IAAI,MAAM,KAAK,SAAS;gBAAE,IAAI,CAAC,gBAAgB,CAAC,MAAM,CAAC,MAAM,CAAC,CAAC;QACjE,CAAC;IACH,CAAC;IAEO,KAAK,CAAC,WAAW;QACvB,IAAI,CAAC;YACH,MAAM,GAAG,GAAG,MAAM,GAAG,CAAC,QAAQ,CAAC,IAAI,CAAC,SAAS,EAAE,OAAO,CAAC,CAAC;YACxD,OAAO,IAAI,CAAC,KAAK,CAAC,GAAG,CAAsB,CAAC;QAC9C,CAAC;QAAC,MAAM,CAAC;YACP,OAAO,SAAS,CAAC;QACnB,CAAC;IACH,CAAC;IAEO,KAAK,CAAC,cAAc;QAC1B,IAAI,CAAC,IAAI,CAAC,WAAW;YAAE,OAAO;QAC9B,MAAM,GAAG,GAAG,IAAI,CAAC,OAAO,CAAC,IAAI,CAAC,SAAS,CAAC,CAAC;QACzC,MAAM,GAAG,CAAC,KAAK,CAAC,GAAG,EAAE,EAAE,SAAS,EAAE,IAAI,EAAE,IAAI,EAAE,KAAK,EAAE,CAAC,CAAC;QACvD,MAAM,OAAO,GAAsB,EAAE,WAAW,EAAE,IAAI,CAAC,WAAW,EAAE,aAAa,EAAE,IAAI,CAAC,aAAa,EAAE,CAAC;QACxG,MAAM,GAAG,CAAC,SAAS,CAAC,IAAI,CAAC,SAAS,EAAE,IAAI,CAAC,SAAS,CAAC,OAAO,CAAC,EAAE,EAAE,IAAI,EAAE,KAAK,EAAE,CAAC,CAAC;IAChF,CAAC;CACF;AA7QD,sCA6QC;AAED,SAAS,KAAK,CAAC,EAAU;IACvB,OAAO,IAAI,OAAO,CAAC,CAAC,OAAO,EAAE,EAAE,CAAC,UAAU,CAAC,OAAO,EAAE,EAAE,CAAC,CAAC,CAAC;AAC3D,CAAC;AAED,0EAA0E;AAC1E,6EAA6E;AAC7E,SAAgB,qBAAqB,CAAC,SAAiB;IACrD,OAAO,EAAE,CAAC,UAAU,CAAC,eAAe,CAAC,SAAS,CAAC,CAAC,CAAC;AACnD,CAAC"}
|
package/mcp/server.ts
CHANGED
|
@@ -18,6 +18,7 @@ import { LineModule } from './tools/line/module';
|
|
|
18
18
|
import { SlackModule } from './tools/slack/module';
|
|
19
19
|
import { WhatsAppModule } from './tools/whatsapp/module';
|
|
20
20
|
import { WhatsAppCloudModule } from './tools/whatsapp-cloud/module';
|
|
21
|
+
import { WeChatModule } from './tools/wechat/module';
|
|
21
22
|
import { CronModule } from './tools/cron/module';
|
|
22
23
|
import { SkillsModule } from './tools/skills/module';
|
|
23
24
|
import { AgentModule } from './tools/agent/module';
|
|
@@ -46,6 +47,7 @@ const modules: AnyModule[] = [
|
|
|
46
47
|
new SlackModule(),
|
|
47
48
|
new WhatsAppModule(),
|
|
48
49
|
new WhatsAppCloudModule(),
|
|
50
|
+
new WeChatModule(),
|
|
49
51
|
new CronModule(),
|
|
50
52
|
new SkillsModule(),
|
|
51
53
|
new AgentModule(),
|
|
@@ -0,0 +1,49 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* HTTP client for the gateway's own WeChat REST API — never a direct iLink
|
|
3
|
+
* call from inside the agent's sandbox. Mirrors `mcp/tools/cron/client.ts`'s
|
|
4
|
+
* shape: this subprocess has no route to the live long-poll session the main
|
|
5
|
+
* gateway process holds in memory (per agent), so sending has to go through
|
|
6
|
+
* that process's own `/wechat/send` route, the same way WhatsApp's Baileys
|
|
7
|
+
* socket is reached (see src/api/router.ts's `/whatsapp/send` doc comment
|
|
8
|
+
* for the same reasoning, once that channel lands).
|
|
9
|
+
*/
|
|
10
|
+
|
|
11
|
+
export class WeChatClient {
|
|
12
|
+
private readonly baseUrl: string;
|
|
13
|
+
private readonly agentId: string;
|
|
14
|
+
private readonly apiKey: string;
|
|
15
|
+
|
|
16
|
+
constructor(apiUrl: string, agentId: string, apiKey?: string) {
|
|
17
|
+
this.baseUrl = apiUrl.replace(/\/$/, '');
|
|
18
|
+
this.agentId = agentId;
|
|
19
|
+
this.apiKey = apiKey ?? '';
|
|
20
|
+
}
|
|
21
|
+
|
|
22
|
+
private url(path: string): string {
|
|
23
|
+
return `${this.baseUrl}/api/v1/agents/${this.agentId}/wechat${path}`;
|
|
24
|
+
}
|
|
25
|
+
|
|
26
|
+
private async request(method: string, path: string, body?: unknown): Promise<unknown> {
|
|
27
|
+
const headers: Record<string, string> = {};
|
|
28
|
+
if (body) headers['Content-Type'] = 'application/json';
|
|
29
|
+
if (this.apiKey) headers['X-Api-Key'] = this.apiKey;
|
|
30
|
+
|
|
31
|
+
const res = await fetch(this.url(path), {
|
|
32
|
+
method,
|
|
33
|
+
headers,
|
|
34
|
+
body: body ? JSON.stringify(body) : undefined,
|
|
35
|
+
});
|
|
36
|
+
|
|
37
|
+
if (!res.ok) {
|
|
38
|
+
const text = await res.text().catch(() => '');
|
|
39
|
+
throw new Error(`WeChat API ${method} ${path} failed: HTTP ${res.status} ${text}`);
|
|
40
|
+
}
|
|
41
|
+
|
|
42
|
+
const contentType = res.headers.get('content-type') ?? '';
|
|
43
|
+
return contentType.includes('application/json') ? res.json() : res.text();
|
|
44
|
+
}
|
|
45
|
+
|
|
46
|
+
async send(toId: string, text: string): Promise<void> {
|
|
47
|
+
await this.request('POST', '/send', { to_id: toId, text });
|
|
48
|
+
}
|
|
49
|
+
}
|