openclaw-openagent 1.0.12 → 1.0.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.
Files changed (132) hide show
  1. package/dist/index.js +2 -0
  2. package/dist/src/config/config-schema.d.ts +9 -0
  3. package/dist/src/config/config-schema.js +6 -0
  4. package/dist/src/messaging/executor.d.ts +2 -3
  5. package/dist/src/messaging/executor.js +4 -31
  6. package/dist/src/plugin-ui/assets/openagent-override.js +124 -18
  7. package/dist/src/proxy/auth-proxy.js +5 -0
  8. package/dist/src/runtime/update-checker.d.ts +18 -0
  9. package/dist/src/runtime/update-checker.js +216 -0
  10. package/index.ts +3 -0
  11. package/package.json +1 -3
  12. package/src/app/channel-tools.ts +0 -249
  13. package/src/app/discovery-tools.ts +0 -273
  14. package/src/app/download-file-tool.ts +0 -133
  15. package/src/app/hooks.ts +0 -144
  16. package/src/app/index.ts +0 -84
  17. package/src/app/messaging-tools.ts +0 -79
  18. package/src/app/ops-tools.ts +0 -155
  19. package/src/app/remote-agent-tool.ts +0 -762
  20. package/src/app/types.ts +0 -68
  21. package/src/app/upload-file-tool.ts +0 -411
  22. package/src/app/verbose-preflight.ts +0 -190
  23. package/src/auth/config.ts +0 -266
  24. package/src/auth/credential-manager.ts +0 -146
  25. package/src/auth/index.ts +0 -24
  26. package/src/auth/verify.ts +0 -99
  27. package/src/channel.ts +0 -566
  28. package/src/compat.ts +0 -94
  29. package/src/config/config-schema.ts +0 -39
  30. package/src/messaging/aggregator.ts +0 -120
  31. package/src/messaging/collector.ts +0 -89
  32. package/src/messaging/executor.ts +0 -72
  33. package/src/messaging/inbound.ts +0 -150
  34. package/src/messaging/index.ts +0 -11
  35. package/src/messaging/mention-protocol.ts +0 -94
  36. package/src/messaging/process-c2c-request.ts +0 -564
  37. package/src/messaging/process-message.ts +0 -373
  38. package/src/messaging/scheduler.ts +0 -55
  39. package/src/messaging/types.ts +0 -38
  40. package/src/plugin-ui/adapters/oc-2026-04.js +0 -103
  41. package/src/plugin-ui/adapters/oc-2026-05.js +0 -125
  42. package/src/plugin-ui/adapters/oc-2026-06.js +0 -125
  43. package/src/plugin-ui/adapters/oc-unknown.js +0 -48
  44. package/src/plugin-ui/assets/agentbook-icon.svg +0 -5
  45. package/src/plugin-ui/assets/bg.png +0 -0
  46. package/src/plugin-ui/assets/icon.png +0 -0
  47. package/src/plugin-ui/assets/magic.svg +0 -5
  48. package/src/plugin-ui/assets/openagent-override.js +0 -11156
  49. package/src/plugin-ui/build.cjs +0 -463
  50. package/src/plugin-ui/index.ts +0 -18
  51. package/src/plugin-ui/modules/agent-book/panel/agent-book.js +0 -570
  52. package/src/plugin-ui/modules/agent-book/panel/agent-card.js +0 -170
  53. package/src/plugin-ui/modules/agent-book/panel/agent-data.js +0 -643
  54. package/src/plugin-ui/modules/agent-book/panel/inject-ui.js +0 -665
  55. package/src/plugin-ui/modules/agent-book/panel/mention-state.js +0 -206
  56. package/src/plugin-ui/modules/agent-book/panel/styles.js +0 -833
  57. package/src/plugin-ui/modules/agent-book/panel/theme-adapter.js +0 -86
  58. package/src/plugin-ui/modules/agent-book/remote-agent-tool/components-core.js +0 -295
  59. package/src/plugin-ui/modules/agent-book/remote-agent-tool/thought-chain-card.js +0 -211
  60. package/src/plugin-ui/modules/agent-book/scanner.js +0 -131
  61. package/src/plugin-ui/modules/agent-book/travelcard/travel-cards.js +0 -500
  62. package/src/plugin-ui/modules/agent-book/travelcard/travel-engine.js +0 -652
  63. package/src/plugin-ui/modules/agent-book/travelcard/travel-styles.js +0 -256
  64. package/src/plugin-ui/modules/loader/bootstrap.js +0 -38
  65. package/src/plugin-ui/modules/loader/shared-state.js +0 -838
  66. package/src/plugin-ui/modules/loader/ws-intercept.js +0 -199
  67. package/src/plugin-ui/modules/remote-agent/chunk-parser.js +0 -161
  68. package/src/plugin-ui/modules/remote-agent/execution-card.js +0 -530
  69. package/src/plugin-ui/modules/remote-agent/markdown-renderer.js +0 -256
  70. package/src/plugin-ui/modules/remote-agent/media-links.js +0 -151
  71. package/src/plugin-ui/modules/remote-agent/native-style-adapter.js +0 -134
  72. package/src/plugin-ui/modules/remote-agent/output-card.js +0 -342
  73. package/src/plugin-ui/modules/remote-agent/progress-store.js +0 -363
  74. package/src/plugin-ui/modules/remote-agent/render-hooks.js +0 -1700
  75. package/src/plugin-ui/modules/remote-agent/styles.js +0 -896
  76. package/src/plugin-ui/modules/remote-agent/tool-card-model.js +0 -130
  77. package/src/plugin-ui/postinstall-deploy.cjs +0 -52
  78. package/src/plugin-ui/ui-extension-loader/backup.ts +0 -92
  79. package/src/plugin-ui/ui-extension-loader/index.ts +0 -276
  80. package/src/plugin-ui/ui-extension-loader/locator.ts +0 -152
  81. package/src/plugin-ui/ui-extension-loader/manifest.ts +0 -57
  82. package/src/plugin-ui/ui-extension-loader/registry-regex.ts +0 -944
  83. package/src/plugin-ui/ui-extension-loader/removed-extensions.ts +0 -70
  84. package/src/plugin-ui/ui-extension-loader/types.ts +0 -72
  85. package/src/proxy/auth-proxy.ts +0 -409
  86. package/src/runtime/account.ts +0 -549
  87. package/src/runtime/index.ts +0 -7
  88. package/src/runtime/plugin-runtime.ts +0 -94
  89. package/src/runtime/registry.ts +0 -71
  90. package/src/sdk/CLASS_MAP.md +0 -143
  91. package/src/sdk/index.d.ts +0 -126
  92. package/src/sdk/index.js +0 -23990
  93. package/src/sdk/modules/cloud-search-module.js +0 -1117
  94. package/src/sdk/modules/follow-module.js +0 -1069
  95. package/src/sdk/modules/group-module.js +0 -7397
  96. package/src/sdk/modules/relationship-module.js +0 -2269
  97. package/src/sdk/modules/signaling-module.js +0 -1468
  98. package/src/sdk/modules/tim-upload-plugin.js +0 -730
  99. package/src/sdk/node-env/http-request.js +0 -90
  100. package/src/sdk/node-env/index.js +0 -57
  101. package/src/sdk/node-env/storage.js +0 -114
  102. package/src/sdk/package.json +0 -10
  103. package/src/sdk/tsconfig.json +0 -16
  104. package/src/state/pending-invocation-store.ts +0 -43
  105. package/src/state/store.ts +0 -756
  106. package/src/tim/c2c.ts +0 -451
  107. package/src/tim/channels.ts +0 -364
  108. package/src/tim/client.ts +0 -330
  109. package/src/tim/index.ts +0 -18
  110. package/src/tim/messages.ts +0 -166
  111. package/src/tim/sdk-logger-init.ts +0 -50
  112. package/src/tools.ts +0 -10
  113. package/src/transport/factory.ts +0 -95
  114. package/src/transport/oasn/index.ts +0 -17
  115. package/src/transport/oasn/oasn-agent-card.ts +0 -111
  116. package/src/transport/oasn/oasn-discovery.ts +0 -108
  117. package/src/transport/oasn/oasn-files.ts +0 -210
  118. package/src/transport/oasn/oasn-http.ts +0 -529
  119. package/src/transport/oasn/oasn-invocation.ts +0 -604
  120. package/src/transport/oasn/oasn-normalize.ts +0 -133
  121. package/src/transport/oasn/oasn-register.ts +0 -33
  122. package/src/transport/oasn/oasn-transport.ts +0 -318
  123. package/src/transport/oasn/oasn-types.ts +0 -404
  124. package/src/transport/tim/index.ts +0 -8
  125. package/src/transport/tim/tim-transport.ts +0 -515
  126. package/src/transport/types.ts +0 -538
  127. package/src/types/openclaw-plugin-sdk-media-store.d.ts +0 -9
  128. package/src/types/openclaw.d.ts +0 -97
  129. package/src/types/tencentcloud-chat.d.ts +0 -15
  130. package/src/util/http.ts +0 -113
  131. package/src/util/logger.ts +0 -131
  132. package/src/util/url-resolver.ts +0 -77
@@ -1,373 +0,0 @@
1
- /**
2
- * Process Message — Core inbound dispatch pipeline
3
- *
4
- * ⚠️ TIM-only 路径(v3.9+ 双轨抽象)
5
- * ---------------------------------------------------------
6
- * 仅在 transport='tim' 下被 AccountRuntime._connectTIM() 通过
7
- * `this.client.on('message', ...)` 注册。OASN 路径下没有 WebSocket 群聊消息,
8
- * 该 pipeline 整体不参与运行。
9
- *
10
- * Replaces the old 4-module pipeline (Collector→Aggregator→Scheduler→Executor)
11
- * with OpenClaw's standard channelRuntime dispatch:
12
- *
13
- * 1. Self-message filter
14
- * 2. channelRuntime safety check
15
- * 3. Append to channel history ring buffer
16
- * 4. Fetch group context (name, skill)
17
- * 5. TIM → MsgContext conversion (inbound.ts) with enriched context
18
- * 6. Agent routing (channelRuntime.routing.resolveAgentRoute)
19
- * 7. Finalize context (channelRuntime.reply.finalizeInboundContext)
20
- * 8. Record session (channelRuntime.session.recordInboundSession)
21
- * 9. Create reply dispatcher (channelRuntime.reply.createReplyDispatcherWithTyping)
22
- * 10. Dispatch AI reply (channelRuntime.reply.dispatchReplyFromConfig)
23
- *
24
- * v3.4.0: Added InboundHistory ring buffer and GroupSystemPrompt/GroupSubject
25
- * injection to fix LLM NO_REPLY conversation breaks.
26
- * See: docs/audit/008-inbound-context-gap.md
27
- *
28
- * Reference: docs/reference/plugins/openclaw-weixin/src/messaging/process-message.ts
29
- */
30
-
31
- import type { PluginRuntime } from 'openclaw/plugin-sdk/core';
32
-
33
- import { timMessageToMsgContext } from './inbound.js';
34
- import type { InboundHistoryEntry } from './inbound.js';
35
- import type { RawPushMessage } from '../tim/client.js';
36
- import { buildMentionPrompt, extractAtTargets } from './mention-protocol.js';
37
- import type { MentionMember } from './mention-protocol.js';
38
-
39
- // ── Types ──
40
-
41
- /** Dependencies injected by the caller (AccountRuntime). */
42
- export interface ProcessMessageDeps {
43
- accountId: string;
44
- selfUserId: string;
45
- config: Record<string, unknown>;
46
- channelRuntime: PluginRuntime['channel'];
47
- sendMessage: (channelId: string, text: string, atUserList?: string[]) => Promise<void>;
48
- /** Fetch channel skill/rules (stored in TIM group notification). */
49
- getChannelSkill?: (channelId: string) => Promise<string | null>;
50
- /** Fetch channel display name. */
51
- getGroupName?: (channelId: string) => Promise<string | null>;
52
- /** Fetch a group-level custom field (AppDefinedData). */
53
- getGroupCustomField?: (channelId: string, key: string) => Promise<string | null>;
54
- /** Fetch group member list for mention protocol injection. */
55
- getGroupMembers?: (channelId: string) => Promise<MentionMember[]>;
56
- log: {
57
- info: (msg: string) => void;
58
- warn: (msg: string) => void;
59
- error: (msg: string) => void;
60
- debug: (msg: string) => void;
61
- };
62
- }
63
-
64
- // ── InboundHistory ring buffer ──
65
-
66
- /**
67
- * In-memory per-channel message history.
68
- * Provides InboundHistory to LLM so it has conversation context.
69
- *
70
- * FIFO ring buffer: oldest messages are evicted when limit is reached.
71
- * This is volatile (lost on restart), which is acceptable — LLM gets
72
- * at least the recent conversation since last connection.
73
- */
74
- const HISTORY_LIMIT = 20;
75
- const channelHistories = new Map<string, InboundHistoryEntry[]>();
76
-
77
- function appendHistory(
78
- channelId: string,
79
- entry: InboundHistoryEntry,
80
- ): void {
81
- let arr = channelHistories.get(channelId);
82
- if (!arr) {
83
- arr = [];
84
- channelHistories.set(channelId, arr);
85
- }
86
- arr.push(entry);
87
- if (arr.length > HISTORY_LIMIT) arr.shift(); // FIFO eviction
88
- }
89
-
90
- function getHistory(channelId: string): InboundHistoryEntry[] {
91
- return [...(channelHistories.get(channelId) ?? [])];
92
- }
93
-
94
- // ── Group name cache ──
95
-
96
- /**
97
- * Simple in-memory cache for group names to avoid repeated SDK calls.
98
- * No TTL — group names rarely change during a session.
99
- */
100
- const groupNameCache = new Map<string, string>();
101
-
102
- /**
103
- * Per-channel gm_req_mention cache.
104
- * "1" = mention-only mode (only @ triggers LLM).
105
- * "0" or absent = default mode (LLM receives all messages).
106
- */
107
- const requireMentionCache = new Map<string, string>();
108
-
109
-
110
- // ── Per-channel promise queue ──
111
-
112
- const channelQueues = new Map<string, Promise<void>>();
113
-
114
- /**
115
- * Enqueue message processing per channel to prevent concurrent AI turns
116
- * on the same channel (which would cause interleaved replies).
117
- *
118
- * Each channel gets its own serial queue. Failures in one message
119
- * do NOT block subsequent messages (.catch(() => undefined)).
120
- *
121
- * Reference: openclaw-weixin / yuanbao enqueueForConversation pattern.
122
- */
123
- function enqueueForChannel(
124
- channelId: string,
125
- task: () => Promise<void>,
126
- ): void {
127
- const prev = channelQueues.get(channelId) ?? Promise.resolve();
128
- const next = prev
129
- .catch(() => undefined)
130
- .then(() => task())
131
- .catch(() => undefined);
132
- channelQueues.set(channelId, next);
133
- }
134
-
135
- // ── Core processing ──
136
-
137
- /**
138
- * Process a single inbound TIM push message through the standard
139
- * OpenClaw channelRuntime pipeline.
140
- *
141
- * This function is fire-and-forget safe — errors are caught and logged,
142
- * never propagated to crash the TIM event listener.
143
- */
144
- export async function processOneMessage(
145
- raw: RawPushMessage,
146
- deps: ProcessMessageDeps,
147
- ): Promise<void> {
148
- // Step 1: Self-message filter
149
- // Record self-messages in history (so LLM sees its own replies in context),
150
- // but don't process them through the AI pipeline.
151
- if (raw.from === deps.selfUserId) {
152
- appendHistory(raw.channelId, {
153
- sender: '(you)',
154
- body: raw.text,
155
- timestamp: raw.time,
156
- });
157
- deps.log.debug(`[process-message] skip self msg id=${raw.id} (recorded in history)`);
158
- return;
159
- }
160
-
161
- // Step 2: channelRuntime safety check
162
- if (!deps.channelRuntime) {
163
- deps.log.error(`[process-message] channelRuntime is undefined, skip msg id=${raw.id}`);
164
- return;
165
- }
166
-
167
- // Queue per channel to serialize AI turns
168
- enqueueForChannel(raw.channelId, () => _processOneMessageInner(raw, deps));
169
- }
170
-
171
- async function _processOneMessageInner(
172
- raw: RawPushMessage,
173
- deps: ProcessMessageDeps,
174
- ): Promise<void> {
175
- const { channelRuntime, log } = deps;
176
-
177
- // Step 3: Record this message in history BEFORE processing
178
- // (so the LLM sees all prior messages, but not the current one which is Body)
179
- const historySnapshot = getHistory(raw.channelId);
180
-
181
- // Append current message to history for future turns
182
- appendHistory(raw.channelId, {
183
- sender: raw.nick || raw.from,
184
- body: raw.text,
185
- timestamp: raw.time,
186
- });
187
-
188
- // Step 4: Fetch group context (cached where possible)
189
- let groupName: string | undefined;
190
- let groupSystemPrompt: string | undefined;
191
-
192
- // Group name (cached)
193
- if (groupNameCache.has(raw.channelId)) {
194
- groupName = groupNameCache.get(raw.channelId);
195
- } else if (deps.getGroupName) {
196
- try {
197
- const name = await deps.getGroupName(raw.channelId);
198
- if (name) {
199
- groupName = name;
200
- groupNameCache.set(raw.channelId, name);
201
- }
202
- } catch (err) {
203
- log.warn(`[process-message] getGroupName failed: ${(err as Error).message}`);
204
- }
205
- }
206
-
207
- // Group system prompt (not cached — may change between messages)
208
- if (deps.getChannelSkill) {
209
- try {
210
- const skill = await deps.getChannelSkill(raw.channelId);
211
- if (skill) groupSystemPrompt = skill;
212
- } catch (err) {
213
- log.warn(`[process-message] getChannelSkill failed: ${(err as Error).message}`);
214
- }
215
- }
216
-
217
- // gm_req_mention (cached)
218
- let requireMention = false;
219
- if (requireMentionCache.has(raw.channelId)) {
220
- requireMention = requireMentionCache.get(raw.channelId) === '1';
221
- } else if (deps.getGroupCustomField) {
222
- try {
223
- const val = await deps.getGroupCustomField(raw.channelId, 'gm_req_mention');
224
- requireMentionCache.set(raw.channelId, val ?? '0');
225
- requireMention = val === '1';
226
- } catch (err) {
227
- log.warn(`[process-message] gm_req_mention fetch failed: ${(err as Error).message}`);
228
- }
229
- }
230
-
231
- // Step 4.5: Mention protocol — fetch members + inject rules (only in mention mode)
232
- // Always fetch fresh from TIM SDK (it hits the server each call).
233
- // Do NOT cache: members can join/leave at any time.
234
- // See: docs/audit/013-mention-at-delivery-failure-v3.4.5.md
235
- let groupMembers: MentionMember[] | undefined;
236
- if (requireMention && deps.getGroupMembers) {
237
- try {
238
- groupMembers = await deps.getGroupMembers(raw.channelId);
239
- } catch (err) {
240
- log.warn(`[process-message] getGroupMembers failed: ${(err as Error).message}`);
241
- }
242
-
243
- if (groupMembers && groupMembers.length > 0) {
244
- const mentionRule = buildMentionPrompt(groupMembers, deps.selfUserId);
245
- if (mentionRule) {
246
- groupSystemPrompt = groupSystemPrompt
247
- ? `${groupSystemPrompt}\n\n${mentionRule}`
248
- : mentionRule;
249
- }
250
- }
251
- }
252
-
253
- // Step 5: Convert TIM message to standard MsgContext with enriched context
254
- const ctx = timMessageToMsgContext(raw, deps.accountId, {
255
- groupName,
256
- groupSystemPrompt,
257
- inboundHistory: historySnapshot.length > 0 ? historySnapshot : undefined,
258
- });
259
-
260
- log.info(
261
- `[process-message] inbound from=${ctx.From} ch=${ctx.To} bodyLen=${ctx.Body.length} mention=${String(ctx.WasMentioned)} reqMention=${String(requireMention)} historyLen=${historySnapshot.length}`,
262
- );
263
-
264
- // Step 5.5: Mention-only gate
265
- // When gm_req_mention="1", only @-mentioned messages trigger LLM.
266
- // Non-mentioned messages are already recorded in history (Step 3),
267
- // so context is preserved for when the agent IS mentioned.
268
- if (requireMention && !ctx.WasMentioned) {
269
- log.info(
270
- `[process-message] mention_only: skip LLM ch=${ctx.To} from=${ctx.From}`,
271
- );
272
- return;
273
- }
274
-
275
- // Step 6: Agent routing
276
- const route = channelRuntime.routing.resolveAgentRoute({
277
- cfg: deps.config,
278
- channel: 'openagent',
279
- accountId: deps.accountId,
280
- peer: { kind: 'group', id: ctx.To },
281
- });
282
-
283
- log.debug(
284
- `[process-message] route: agentId=${route.agentId ?? '(none)'} sessionKey=${route.sessionKey ?? '(none)'}`,
285
- );
286
-
287
- if (!route.agentId) {
288
- log.error(`[process-message] no agentId resolved for ch=${ctx.To}, skipping`);
289
- return;
290
- }
291
-
292
- // Propagate resolved session key
293
- ctx.SessionKey = route.sessionKey;
294
-
295
- // Step 7: Finalize inbound context
296
- const finalized = channelRuntime.reply.finalizeInboundContext(
297
- ctx as Parameters<typeof channelRuntime.reply.finalizeInboundContext>[0],
298
- );
299
-
300
- const fin = finalized as Record<string, unknown>;
301
-
302
- log.debug(
303
- `[process-message] finalized: From=${fin.From} To=${fin.To} GroupSubject=${fin.GroupSubject ?? '(none)'}`,
304
- );
305
-
306
- // Step 8: Record inbound session
307
- const storePath = channelRuntime.session.resolveStorePath(
308
- (deps.config as { session?: { store?: unknown } }).session?.store,
309
- { agentId: route.agentId },
310
- );
311
-
312
- await channelRuntime.session.recordInboundSession({
313
- storePath,
314
- sessionKey: route.sessionKey,
315
- ctx: finalized as Parameters<typeof channelRuntime.session.recordInboundSession>[0]['ctx'],
316
- updateLastRoute: {
317
- sessionKey: route.mainSessionKey,
318
- channel: 'openagent',
319
- to: ctx.To,
320
- accountId: deps.accountId,
321
- },
322
- onRecordError: (err: unknown) => log.error(`[process-message] recordInboundSession error: ${String(err)}`),
323
- });
324
-
325
- log.debug(`[process-message] session recorded, storePath=${storePath}`);
326
-
327
- // Step 9: Create reply dispatcher with deliver callback
328
- const { dispatcher, replyOptions, markDispatchIdle } =
329
- channelRuntime.reply.createReplyDispatcherWithTyping({
330
- deliver: async (payload: { text?: string; mediaUrl?: string; mediaUrls?: string[] }) => {
331
- const text = payload.text ?? '';
332
- if (!text) {
333
- log.debug('[process-message] deliver: empty text, skip');
334
- return;
335
- }
336
-
337
- // Extract @-mention targets from AI output (mention mode only)
338
- const atUserList = (requireMention && groupMembers)
339
- ? extractAtTargets(text, groupMembers, deps.selfUserId)
340
- : undefined;
341
- const effectiveAtList = atUserList && atUserList.length > 0 ? atUserList : undefined;
342
-
343
- log.info(`[process-message] deliver: ch=${ctx.To} textLen=${text.length} at=${effectiveAtList?.join(',') ?? 'none'}`);
344
- await deps.sendMessage(ctx.To, text, effectiveAtList);
345
- log.debug(`[process-message] deliver: sent OK`);
346
- },
347
- onError: (err: unknown, info: { kind: string }) => {
348
- log.error(`[process-message] reply ${info.kind} error: ${String(err)}`);
349
- },
350
- });
351
-
352
- // Step 10: Dispatch AI reply
353
- log.debug(`[process-message] dispatching AI turn agentId=${route.agentId}`);
354
- try {
355
- await channelRuntime.reply.withReplyDispatcher({
356
- dispatcher,
357
- run: () =>
358
- channelRuntime.reply.dispatchReplyFromConfig({
359
- ctx: finalized,
360
- cfg: deps.config,
361
- dispatcher,
362
- replyOptions: { ...replyOptions, disableBlockStreaming: true },
363
- }),
364
- });
365
- log.info(`[process-message] AI turn completed for ch=${ctx.To}`);
366
- } catch (err) {
367
- log.error(
368
- `[process-message] dispatchReplyFromConfig error: ${(err as Error).message}`,
369
- );
370
- } finally {
371
- markDispatchIdle();
372
- }
373
- }
@@ -1,55 +0,0 @@
1
- /**
2
- * Scheduler — Serial inbound queue with priority ordering
3
- *
4
- * Mention-containing deltas are pushed to the front of the queue.
5
- * Processing is serial to avoid concurrent agent turns.
6
- */
7
-
8
- import { logger } from '../util/logger.js';
9
- import type { ChannelDelta } from './types.js';
10
- import type { ActionExecutor } from './executor.js';
11
-
12
- export class Scheduler {
13
- private executor: ActionExecutor;
14
- private queue: ChannelDelta[] = [];
15
- private _processing = false;
16
-
17
- constructor(executor: ActionExecutor) {
18
- this.executor = executor;
19
- }
20
-
21
- enqueue(delta: ChannelDelta): void {
22
- if (delta.hasMention) {
23
- this.queue.unshift(delta);
24
- } else {
25
- this.queue.push(delta);
26
- }
27
-
28
- logger.debug(
29
- `[scheduler] ENQUEUE ch=${delta.channelId} pos=${delta.hasMention ? 'FRONT' : 'BACK'} queue=${this.queue.length}`,
30
- );
31
- void this._processNext();
32
- }
33
-
34
- private async _processNext(): Promise<void> {
35
- if (this._processing || this.queue.length === 0) return;
36
- this._processing = true;
37
-
38
- try {
39
- const delta = this.queue.shift()!;
40
- logger.debug(`[scheduler] PROCESS ch=${delta.channelId} msgs=${delta.messageCount} remaining=${this.queue.length}`);
41
- await this.executor.handleDelta(delta);
42
- } catch (err) {
43
- logger.error(`[scheduler] ERROR processing delta: ${(err as Error).message}`);
44
- } finally {
45
- this._processing = false;
46
- if (this.queue.length > 0) {
47
- setTimeout(() => void this._processNext(), 0);
48
- }
49
- }
50
- }
51
-
52
- get queueSize(): number {
53
- return this.queue.length;
54
- }
55
- }
@@ -1,38 +0,0 @@
1
- /**
2
- * Messaging — Shared type definitions
3
- */
4
-
5
- import type { RawPushMessage } from '../tim/client.js';
6
-
7
- /**
8
- * A raw message from any source (push or history).
9
- * Push messages come from TIM SDK events.
10
- */
11
- export type RawMessage = RawPushMessage;
12
-
13
- /**
14
- * A batch of messages ready for agent processing.
15
- * Built by the WindowAggregator when flush conditions are met.
16
- */
17
- export interface ChannelDelta {
18
- channelId: string;
19
- channelName: string;
20
- messageCount: number;
21
- participants: string[];
22
- hasMention: boolean;
23
- urgency: number;
24
- messages: RawMessage[];
25
- source: string;
26
- flushReason: string;
27
- }
28
-
29
- /**
30
- * SDK message format for fetchMessages (see tim/messages.ts).
31
- */
32
- export interface HistoryMessage {
33
- id: string;
34
- from: string;
35
- text: string;
36
- time: number;
37
- seq?: number;
38
- }
@@ -1,103 +0,0 @@
1
- // ── OpenClaw 2026.4 host adapter ──
2
- // Host DOM: chat-tool-msg-collapse -> chat-tool-msg-body -> chat-tool-card.
3
-
4
- (function _clInstallHostAdapter202604() {
5
- function _matches(node, selector) {
6
- return !!(node && selector && node.matches && node.matches(selector));
7
- }
8
-
9
- var adapter = {
10
- id: 'oc-2026-04',
11
- family: '2026.4',
12
- css: {
13
- remoteShell: [
14
- 'details.chat-tool-msg-collapse:has(.cl-remote-agent-card)',
15
- '.chat-tool-msg-collapse:has(.cl-remote-agent-card)',
16
- ],
17
- outputHostMargin: [],
18
- outputHostMarginReset: [
19
- 'details.chat-tool-msg-collapse:has(.cl-remote-agent-card)',
20
- '.chat-tool-msg-collapse:has(.cl-remote-agent-card)',
21
- ],
22
- summaryHidden: [
23
- 'details.chat-tool-msg-collapse:has(.cl-remote-agent-card) > summary.chat-tool-msg-summary',
24
- '.chat-tool-msg-collapse:has(.cl-remote-agent-card) > .chat-tool-msg-summary',
25
- ],
26
- hostShellRawText: [
27
- '.chat-tool-msg-body.cl-remote-agent-host-shell > .chat-text',
28
- ],
29
- rawTextCardHosts: [
30
- '.chat-tool-msg-body:has(.cl-remote-agent-card) > .chat-text',
31
- '.chat-tool-card__detail:has(.cl-remote-agent-card) > .chat-text',
32
- ],
33
- rawTextPlaceholderHosts: [
34
- '.chat-tool-msg-body:has(.cl-remote-agent-output-placeholder) > .chat-text',
35
- '.chat-tool-card__detail:has(.cl-remote-agent-output-placeholder) > .chat-text',
36
- ],
37
- hostBody: [
38
- 'details.chat-tool-msg-collapse:has(.cl-remote-agent-card) > .chat-tool-msg-body',
39
- '.chat-tool-msg-collapse:has(.cl-remote-agent-card) > .chat-tool-msg-body',
40
- ],
41
- manualOpenReset: [
42
- '.chat-tool-msg-collapse.chat-tool-msg-collapse--manual.is-open:has(.cl-remote-agent-card)',
43
- ],
44
- hostShellReset: [
45
- '.cl-remote-agent-host-shell.chat-tool-card',
46
- '.cl-remote-agent-host-shell.chat-tool-card__detail',
47
- '.cl-remote-agent-host-shell.chat-tool-msg-body',
48
- 'details.cl-remote-agent-host-shell',
49
- ],
50
- hostShellSummary: [
51
- '.cl-remote-agent-host-shell > summary.chat-tool-msg-summary',
52
- '.cl-remote-agent-host-shell > .chat-tool-msg-summary',
53
- ],
54
- modernCardLayout: false,
55
- },
56
- nativeStyle: {
57
- shellSelectors: [
58
- '.chat-tool-card:not(:has(.cl-remote-agent-card))',
59
- '.chat-tool-msg-collapse:not(:has(.cl-remote-agent-card))',
60
- ],
61
- summarySelectors: [
62
- '.chat-tool-card__header',
63
- '.chat-tool-card__title',
64
- '.chat-tool-msg-summary:not(.cl-remote-agent-host-shell *)',
65
- ],
66
- indentSelectors: [
67
- '.chat-group.tool:not(:has(.cl-remote-agent-card))',
68
- '.chat-bubble:not(:has(.cl-remote-agent-card))',
69
- ],
70
- },
71
- selectors: {
72
- textContext: '.chat-text, .chat-tool-card__detail, .chat-tool-msg-body',
73
- summary: ':scope > .chat-tool-msg-summary, .chat-tool-msg-summary',
74
- forceOpenHeader: '.chat-tool-msg-summary',
75
- rawTextHostClosest: [
76
- '.chat-tool-msg-body',
77
- '.chat-tool-card__detail',
78
- '.chat-bubble',
79
- ],
80
- rawTextHostsWithinShell: '.chat-tool-msg-body, .chat-tool-card__detail, .chat-bubble',
81
- },
82
- isRemoteNativeToolShellCandidate: function(node) {
83
- return _matches(node, 'details.chat-tool-msg-collapse, .chat-tool-msg-collapse, .chat-tool-card');
84
- },
85
- isNativeToolShell: function(node) {
86
- return _matches(node, 'details.chat-tool-msg-collapse, .chat-tool-msg-collapse');
87
- },
88
- isToolLikeShell: function(node) {
89
- return _matches(node, 'details.chat-tool-msg-collapse, .chat-tool-msg-collapse, .chat-tool-card, .chat-tool-msg-body, .chat-tool-card__detail');
90
- },
91
- isToolBody: function(node) {
92
- return _matches(node, '.chat-tool-msg-body');
93
- },
94
- isMarkableHost: function(node) {
95
- return _matches(node, 'details.chat-tool-msg-collapse, .chat-tool-card, .chat-tool-card__detail, .chat-tool-msg-body');
96
- },
97
- };
98
-
99
- CL.hostAdapter = adapter;
100
- try {
101
- document.documentElement.setAttribute('data-openagent-host-adapter', adapter.id);
102
- } catch (e) {}
103
- })();
@@ -1,125 +0,0 @@
1
- // ── OpenClaw 2026.5 host adapter ──
2
- // Host DOM uses the newer tools-collapse family, with msg-collapse kept as a
3
- // compatible secondary path for mixed 2026.5 builds.
4
-
5
- (function _clInstallHostAdapter202605() {
6
- function _matches(node, selector) {
7
- return !!(node && selector && node.matches && node.matches(selector));
8
- }
9
-
10
- var adapter = {
11
- id: 'oc-2026-05',
12
- family: '2026.5',
13
- css: {
14
- remoteShell: [
15
- 'details.chat-tools-collapse:has(.cl-remote-agent-card)',
16
- 'details.chat-tool-msg-collapse:has(.cl-remote-agent-card)',
17
- '.chat-tools-collapse:has(.cl-remote-agent-card)',
18
- '.chat-tool-msg-collapse:has(.cl-remote-agent-card)',
19
- ],
20
- outputHostMargin: [
21
- 'details.chat-tools-collapse:has(.cl-output-card)',
22
- '.chat-tools-collapse:has(.cl-output-card)',
23
- 'details.chat-tool-msg-collapse:has(.cl-remote-agent-card)',
24
- '.chat-tool-msg-collapse:has(.cl-remote-agent-card)',
25
- ],
26
- outputHostMarginReset: [],
27
- summaryHidden: [
28
- 'details.chat-tools-collapse:has(.cl-remote-agent-card) > summary.chat-tools-summary',
29
- 'details.chat-tool-msg-collapse:has(.cl-remote-agent-card) > summary.chat-tool-msg-summary',
30
- '.chat-tools-collapse:has(.cl-remote-agent-card) > .chat-tools-summary',
31
- '.chat-tool-msg-collapse:has(.cl-remote-agent-card) > .chat-tool-msg-summary',
32
- ],
33
- hostShellRawText: [
34
- '.chat-tools-collapse__body.cl-remote-agent-host-shell > .chat-text',
35
- '.chat-tool-msg-body.cl-remote-agent-host-shell > .chat-text',
36
- ],
37
- rawTextCardHosts: [
38
- '.chat-tools-collapse__body:has(.cl-remote-agent-card) > .chat-text',
39
- '.chat-tool-msg-body:has(.cl-remote-agent-card) > .chat-text',
40
- '.chat-tool-card__detail:has(.cl-remote-agent-card) > .chat-text',
41
- ],
42
- rawTextPlaceholderHosts: [
43
- '.chat-tools-collapse__body:has(.cl-remote-agent-output-placeholder) > .chat-text',
44
- '.chat-tool-msg-body:has(.cl-remote-agent-output-placeholder) > .chat-text',
45
- '.chat-tool-card__detail:has(.cl-remote-agent-output-placeholder) > .chat-text',
46
- ],
47
- hostBody: [
48
- 'details.chat-tools-collapse:has(.cl-remote-agent-card) > .chat-tools-collapse__body',
49
- 'details.chat-tool-msg-collapse:has(.cl-remote-agent-card) > .chat-tool-msg-body',
50
- '.chat-tools-collapse:has(.cl-remote-agent-card) > .chat-tools-collapse__body',
51
- '.chat-tool-msg-collapse:has(.cl-remote-agent-card) > .chat-tool-msg-body',
52
- ],
53
- manualOpenReset: [
54
- '.chat-tool-msg-collapse.chat-tool-msg-collapse--manual.is-open:has(.cl-remote-agent-card)',
55
- ],
56
- hostShellReset: [
57
- '.cl-remote-agent-host-shell.chat-tool-card',
58
- '.cl-remote-agent-host-shell.chat-tool-card__detail',
59
- '.cl-remote-agent-host-shell.chat-tools-collapse__body',
60
- '.cl-remote-agent-host-shell.chat-tool-msg-body',
61
- 'details.cl-remote-agent-host-shell',
62
- ],
63
- hostShellSummary: [
64
- '.cl-remote-agent-host-shell > summary.chat-tools-summary',
65
- '.cl-remote-agent-host-shell > summary.chat-tool-msg-summary',
66
- '.cl-remote-agent-host-shell > .chat-tools-summary',
67
- '.cl-remote-agent-host-shell > .chat-tool-msg-summary',
68
- ],
69
- modernCardLayout: true,
70
- },
71
- nativeStyle: {
72
- shellSelectors: [
73
- '.chat-tool-card:not(:has(.cl-remote-agent-card))',
74
- '.chat-tool-msg-collapse:not(:has(.cl-remote-agent-card))',
75
- '.chat-tools-collapse:not(:has(.cl-remote-agent-card))',
76
- '.tool-card:not(:has(.cl-remote-agent-card))',
77
- '.chat-tool-card__wrapper:not(:has(.cl-remote-agent-card))',
78
- ],
79
- summarySelectors: [
80
- '.chat-tool-card__header',
81
- '.chat-tool-card__title',
82
- '.chat-tool-msg-summary:not(.cl-remote-agent-host-shell *)',
83
- '.chat-tools-summary:not(.cl-remote-agent-host-shell *)',
84
- '.tool-card__header',
85
- '.tool-card__title',
86
- ],
87
- indentSelectors: [
88
- '.chat-group.tool:not(:has(.cl-remote-agent-card))',
89
- '.chat-bubble:not(:has(.cl-remote-agent-card))',
90
- ],
91
- },
92
- selectors: {
93
- textContext: '.chat-text, .chat-tool-card__detail, .chat-tool-msg-body, .chat-tools-collapse__body',
94
- summary: ':scope > summary, :scope > .chat-tools-summary, :scope > .chat-tool-msg-summary, .chat-tools-summary, .chat-tool-msg-summary',
95
- forceOpenHeader: '.chat-tool-msg-summary, .chat-tools-summary',
96
- rawTextHostClosest: [
97
- '.chat-tools-collapse__body',
98
- '.chat-tool-msg-body',
99
- '.chat-tool-card__detail',
100
- '.chat-bubble',
101
- ],
102
- rawTextHostsWithinShell: '.chat-tools-collapse__body, .chat-tool-msg-body, .chat-tool-card__detail, .chat-bubble',
103
- },
104
- isRemoteNativeToolShellCandidate: function(node) {
105
- return _matches(node, 'details.chat-tools-collapse, details.chat-tool-msg-collapse, .chat-tools-collapse, .chat-tool-msg-collapse, .chat-tool-card');
106
- },
107
- isNativeToolShell: function(node) {
108
- return _matches(node, 'details.chat-tools-collapse, details.chat-tool-msg-collapse, .chat-tools-collapse, .chat-tool-msg-collapse');
109
- },
110
- isToolLikeShell: function(node) {
111
- return _matches(node, 'details.chat-tools-collapse, details.chat-tool-msg-collapse, .chat-tools-collapse, .chat-tool-msg-collapse, .chat-tool-card, .chat-tools-collapse__body, .chat-tool-msg-body, .chat-tool-card__detail');
112
- },
113
- isToolBody: function(node) {
114
- return _matches(node, '.chat-tools-collapse__body, .chat-tool-msg-body');
115
- },
116
- isMarkableHost: function(node) {
117
- return _matches(node, 'details.chat-tools-collapse, details.chat-tool-msg-collapse, .chat-tool-card, .chat-tool-card__detail, .chat-tools-collapse__body, .chat-tool-msg-body');
118
- },
119
- };
120
-
121
- CL.hostAdapter = adapter;
122
- try {
123
- document.documentElement.setAttribute('data-openagent-host-adapter', adapter.id);
124
- } catch (e) {}
125
- })();