@agent-wechat/agent-wechat 1.0.0-beta.4 → 1.0.0-beta.5
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/dist/index.js +23 -14
- package/openclaw.plugin.json +2 -0
- package/package.json +2 -1
package/dist/index.js
CHANGED
|
@@ -22,7 +22,7 @@ var nativeConfigSchema = {
|
|
|
22
22
|
}
|
|
23
23
|
}] },
|
|
24
24
|
consumerStateDir: { type: "string" },
|
|
25
|
-
readPolicy: { type: "string", enum: ["never", "on_model_dispatch"] },
|
|
25
|
+
readPolicy: { type: "string", enum: ["never", "on_inbound", "on_model_dispatch"] },
|
|
26
26
|
gatewayFacade: { type: "object", additionalProperties: false, required: ["enabled"], properties: { enabled: { type: "boolean" }, prefix: { type: "string" } } }
|
|
27
27
|
}
|
|
28
28
|
};
|
|
@@ -734,7 +734,7 @@ function collectWeChatStatusIssues(accounts) {
|
|
|
734
734
|
accountId: snapshot.accountId,
|
|
735
735
|
kind: "runtime",
|
|
736
736
|
message: "Prepared model handoff was not confirmed by this OpenClaw host; automatic read state remains unchanged.",
|
|
737
|
-
fix: "
|
|
737
|
+
fix: "Select native.readPolicy=on_inbound to mark successfully handled conversations read without model hooks, or use a compatible prepared-run SDK hook."
|
|
738
738
|
});
|
|
739
739
|
}
|
|
740
740
|
if ((snapshot.needsReview ?? 0) > 0) {
|
|
@@ -1573,7 +1573,7 @@ function nativeWasMentioned(message) {
|
|
|
1573
1573
|
return message.mentions?.state === "known" && message.mentions.self === true;
|
|
1574
1574
|
}
|
|
1575
1575
|
async function projectNativeRead(client, accountId, state) {
|
|
1576
|
-
const pending2 = state.items().filter((value) => value.readPending
|
|
1576
|
+
const pending2 = state.items().filter((value) => value.readPending);
|
|
1577
1577
|
const threads = [...new Set(pending2.map((item) => item.message.threadId))];
|
|
1578
1578
|
for (const threadId of threads) {
|
|
1579
1579
|
for (let attempt = 0; attempt < 2; attempt++) {
|
|
@@ -1604,6 +1604,7 @@ async function projectNativeRead(client, accountId, state) {
|
|
|
1604
1604
|
}
|
|
1605
1605
|
async function dispatchNativeMessage(params) {
|
|
1606
1606
|
const { client, state, account, message, cfg, core } = params;
|
|
1607
|
+
const readPolicy = account.native?.readPolicy ?? "on_inbound";
|
|
1607
1608
|
const custody = state.get(message.id);
|
|
1608
1609
|
if (!custody || custody.state !== "received") return "needs_review";
|
|
1609
1610
|
if (custody.origin !== "live" || message.direction !== "incoming" || ![1, 3, 34, 43, 47, 49].includes(message.type) || message.type === 1 && !message.body || !message.senderId) {
|
|
@@ -1698,7 +1699,7 @@ async function dispatchNativeMessage(params) {
|
|
|
1698
1699
|
assets: preparedMedia.suppliedAssets ?? []
|
|
1699
1700
|
});
|
|
1700
1701
|
state.update(message.id, { state: "dispatching", dispatchManifest });
|
|
1701
|
-
const callback = message.type === 1 || preparedMedia.attachment?.status === "ready" && preparedMedia.suppliedAssets?.length ? state.preparedCallback([message.id],
|
|
1702
|
+
const callback = readPolicy !== "on_inbound" && (message.type === 1 || preparedMedia.attachment?.status === "ready" && preparedMedia.suppliedAssets?.length) ? state.preparedCallback([message.id], readPolicy) : void 0;
|
|
1702
1703
|
if (callback) trackNativePreparedInput(dispatchManifest, callback);
|
|
1703
1704
|
let failed = false;
|
|
1704
1705
|
let delivery = 0;
|
|
@@ -1732,8 +1733,12 @@ async function dispatchNativeMessage(params) {
|
|
|
1732
1733
|
// and media-snapshot bridge; unsupported or ambiguous handoffs leave reads unchanged.
|
|
1733
1734
|
replyOptions: { runId: dispatchManifest.runId, onModelSelected, onPreparedAgentRunStart: callback }
|
|
1734
1735
|
});
|
|
1735
|
-
const
|
|
1736
|
-
state.update(message.id, {
|
|
1736
|
+
const readPending = readPolicy === "on_inbound" && !failed && ingress.ingress.admission === "dispatch" ? true : state.get(message.id)?.readPending;
|
|
1737
|
+
state.update(message.id, {
|
|
1738
|
+
state: failed ? "needs_review" : "completed",
|
|
1739
|
+
readPending,
|
|
1740
|
+
handoffUnconfirmed: readPolicy === "on_model_dispatch" && !state.get(message.id)?.runId
|
|
1741
|
+
});
|
|
1737
1742
|
return failed ? "needs_review" : "completed";
|
|
1738
1743
|
} catch {
|
|
1739
1744
|
state.update(message.id, { state: "needs_review" });
|
|
@@ -1767,9 +1772,12 @@ async function startNativeMonitor(opts) {
|
|
|
1767
1772
|
const core = getWeChatRuntime();
|
|
1768
1773
|
let backoff = 250;
|
|
1769
1774
|
let readTask;
|
|
1770
|
-
const flushRead = () =>
|
|
1771
|
-
|
|
1772
|
-
|
|
1775
|
+
const flushRead = () => {
|
|
1776
|
+
if (native.readPolicy === "never") return Promise.resolve();
|
|
1777
|
+
return readTask ??= projectNativeRead(host2.client, native.accountId, state).finally(() => {
|
|
1778
|
+
readTask = void 0;
|
|
1779
|
+
});
|
|
1780
|
+
};
|
|
1773
1781
|
const process2 = async () => {
|
|
1774
1782
|
const cfg = core.config.current();
|
|
1775
1783
|
const account = resolveWeChatAccount(cfg, opts.account.accountId) ?? opts.account;
|
|
@@ -1788,10 +1796,10 @@ async function startNativeMonitor(opts) {
|
|
|
1788
1796
|
try {
|
|
1789
1797
|
await flushRead();
|
|
1790
1798
|
} catch {
|
|
1791
|
-
opts.log?.error?.("Native read projection is pending;
|
|
1799
|
+
opts.log?.error?.("Native read projection is pending; thread read receipt retained for retry");
|
|
1792
1800
|
}
|
|
1793
1801
|
const needsReview = state.items().filter((value) => value.state === "needs_review" || value.phoneReadState === "needs_review" || value.phoneReadState === "rejected").length;
|
|
1794
|
-
const handoffUnconfirmed = native.readPolicy
|
|
1802
|
+
const handoffUnconfirmed = native.readPolicy === "on_model_dispatch" && state.items().some((value) => value.handoffUnconfirmed);
|
|
1795
1803
|
const accountStatus = await host2.client.account(native.accountId);
|
|
1796
1804
|
opts.setStatus({
|
|
1797
1805
|
accountId: account.accountId,
|
|
@@ -1807,9 +1815,9 @@ async function startNativeMonitor(opts) {
|
|
|
1807
1815
|
await flushRead();
|
|
1808
1816
|
if (!opts.abortSignal.aborted) opts.setStatus({
|
|
1809
1817
|
accountId: opts.account.accountId,
|
|
1810
|
-
handoffUnconfirmed: native.readPolicy
|
|
1818
|
+
handoffUnconfirmed: native.readPolicy === "on_model_dispatch" && state.items().some((value) => value.handoffUnconfirmed)
|
|
1811
1819
|
});
|
|
1812
|
-
}, () => opts.log?.error?.("Native read projection remains pending;
|
|
1820
|
+
}, () => opts.log?.error?.("Native read projection remains pending; thread read receipts retained"));
|
|
1813
1821
|
try {
|
|
1814
1822
|
while (!opts.abortSignal.aborted) {
|
|
1815
1823
|
try {
|
|
@@ -2361,7 +2369,8 @@ var plugin = {
|
|
|
2361
2369
|
api.registerChannel({ plugin: wechatPlugin });
|
|
2362
2370
|
const stopFacade = selected?.native ? registerNativeFacade(api, selected.native) : () => {
|
|
2363
2371
|
};
|
|
2364
|
-
const stopPreparedBoundary = registerNativePreparedBoundary(api)
|
|
2372
|
+
const stopPreparedBoundary = selected?.native?.readPolicy && selected.native.readPolicy !== "on_inbound" ? registerNativePreparedBoundary(api) : () => {
|
|
2373
|
+
};
|
|
2365
2374
|
api.registerService({
|
|
2366
2375
|
id: "agent-wechat-native",
|
|
2367
2376
|
reload: { configPrefixes: ["plugins.entries.agent-wechat.config", "channels.agent-wechat", "secrets"] },
|
package/openclaw.plugin.json
CHANGED
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@agent-wechat/agent-wechat",
|
|
3
|
-
"version": "1.0.0-beta.
|
|
3
|
+
"version": "1.0.0-beta.5",
|
|
4
4
|
"type": "module",
|
|
5
5
|
"files": [
|
|
6
6
|
"dist",
|
|
@@ -183,6 +183,7 @@
|
|
|
183
183
|
"type": "string",
|
|
184
184
|
"enum": [
|
|
185
185
|
"never",
|
|
186
|
+
"on_inbound",
|
|
186
187
|
"on_model_dispatch"
|
|
187
188
|
]
|
|
188
189
|
},
|