@llblab/pi-telegram 0.52.2 → 0.53.1
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/AGENTS.md +9 -7
- package/BACKLOG.md +1 -18
- package/CHANGELOG.md +15 -0
- package/README.md +7 -11
- package/api/commands.ts +3 -0
- package/dist/api/commands.d.ts +1 -1
- package/dist/lib/activity-verbosity.d.ts +1 -5
- package/dist/lib/activity-verbosity.js +15 -42
- package/dist/lib/activity.d.ts +9 -0
- package/dist/lib/activity.js +39 -10
- package/dist/lib/agent-messages.js +7 -3
- package/dist/lib/bindings.d.ts +43 -5
- package/dist/lib/bindings.js +163 -20
- package/dist/lib/bus-api.d.ts +12 -0
- package/dist/lib/bus-api.js +182 -79
- package/dist/lib/bus-follower.d.ts +111 -31
- package/dist/lib/bus-follower.js +1324 -359
- package/dist/lib/bus-leader.d.ts +41 -91
- package/dist/lib/bus-leader.js +969 -637
- package/dist/lib/bus-transport.js +16 -9
- package/dist/lib/bus.d.ts +215 -18
- package/dist/lib/bus.js +1048 -327
- package/dist/lib/channel-posts.d.ts +5 -0
- package/dist/lib/channel-posts.js +434 -261
- package/dist/lib/command-templates.d.ts +26 -5
- package/dist/lib/command-templates.js +92 -176
- package/dist/lib/commands.d.ts +168 -82
- package/dist/lib/commands.js +1409 -291
- package/dist/lib/config.d.ts +1 -8
- package/dist/lib/config.js +34 -76
- package/dist/lib/delivery.d.ts +2 -2
- package/dist/lib/delivery.js +16 -16
- package/dist/lib/extension.js +639 -171
- package/dist/lib/generative-app-worker.mjs +19 -7
- package/dist/lib/generative-apps.d.ts +0 -5
- package/dist/lib/generative-apps.js +61 -49
- package/dist/lib/inbound.d.ts +5 -0
- package/dist/lib/inbound.js +35 -59
- package/dist/lib/journal.d.ts +33 -3
- package/dist/lib/journal.js +2063 -782
- package/dist/lib/lifecycle.d.ts +2 -6
- package/dist/lib/lifecycle.js +75 -58
- package/dist/lib/locks.d.ts +29 -3
- package/dist/lib/locks.js +289 -108
- package/dist/lib/logging.js +50 -14
- package/dist/lib/media.d.ts +22 -1
- package/dist/lib/media.js +46 -28
- package/dist/lib/menu-model.d.ts +19 -5
- package/dist/lib/menu-model.js +53 -11
- package/dist/lib/menu-queue.d.ts +5 -4
- package/dist/lib/menu-queue.js +45 -63
- package/dist/lib/menu-settings.d.ts +5 -4
- package/dist/lib/menu-settings.js +114 -78
- package/dist/lib/menu-status.d.ts +1 -1
- package/dist/lib/menu-status.js +8 -25
- package/dist/lib/menu-thinking.d.ts +6 -1
- package/dist/lib/menu-thinking.js +14 -21
- package/dist/lib/menu.d.ts +8 -61
- package/dist/lib/menu.js +92 -164
- package/dist/lib/model.d.ts +1 -1
- package/dist/lib/model.js +2 -16
- package/dist/lib/outbound-attachments.d.ts +6 -27
- package/dist/lib/outbound-attachments.js +45 -38
- package/dist/lib/outbound-buttons.js +22 -16
- package/dist/lib/outbound-markup.d.ts +0 -2
- package/dist/lib/outbound-markup.js +51 -64
- package/dist/lib/outbound-voice.js +6 -3
- package/dist/lib/outbound.d.ts +6 -6
- package/dist/lib/outbound.js +65 -51
- package/dist/lib/ownership.js +6 -2
- package/dist/lib/paths.d.ts +5 -0
- package/dist/lib/paths.js +37 -21
- package/dist/lib/pi.d.ts +2 -0
- package/dist/lib/pi.js +8 -1
- package/dist/lib/polling.d.ts +21 -37
- package/dist/lib/polling.js +59 -50
- package/dist/lib/preview.js +39 -19
- package/dist/lib/process-identity.d.ts +24 -0
- package/dist/lib/process-identity.js +133 -0
- package/dist/lib/prompts.js +2 -7
- package/dist/lib/queue.d.ts +14 -16
- package/dist/lib/queue.js +252 -127
- package/dist/lib/recovery.d.ts +2 -83
- package/dist/lib/recovery.js +20 -274
- package/dist/lib/replies.d.ts +16 -24
- package/dist/lib/replies.js +99 -116
- package/dist/lib/routing.d.ts +120 -7
- package/dist/lib/routing.js +4667 -1152
- package/dist/lib/runtime.d.ts +1 -11
- package/dist/lib/sections.d.ts +4 -29
- package/dist/lib/sections.js +7 -20
- package/dist/lib/skills.js +4 -3
- package/dist/lib/status.js +86 -57
- package/dist/lib/sync.d.ts +1 -3
- package/dist/lib/sync.js +67 -43
- package/dist/lib/target.d.ts +4 -0
- package/dist/lib/target.js +18 -0
- package/dist/lib/telegram-api.d.ts +18 -13
- package/dist/lib/telegram-api.js +148 -53
- package/dist/lib/text-groups.js +4 -39
- package/dist/lib/thread-cleanup-manager.d.ts +6 -27
- package/dist/lib/thread-cleanup-manager.js +369 -186
- package/dist/lib/thread-display.d.ts +1 -2
- package/dist/lib/thread-display.js +58 -38
- package/dist/lib/thread-naming.d.ts +28 -8
- package/dist/lib/thread-naming.js +175 -66
- package/dist/lib/thread-reconciler.d.ts +42 -16
- package/dist/lib/thread-reconciler.js +90 -50
- package/dist/lib/threads.d.ts +82 -20
- package/dist/lib/threads.js +2247 -855
- package/dist/lib/time-injection.js +1 -2
- package/dist/lib/turns.js +1 -19
- package/dist/lib/updates.d.ts +169 -80
- package/dist/lib/updates.js +2418 -641
- package/dist/lib/voice.d.ts +7 -22
- package/dist/lib/voice.js +7 -22
- package/dist/lib/wire.js +1 -1
- package/dist/lib/workspace-admission.d.ts +3 -1
- package/dist/lib/workspace-admission.js +425 -211
- package/dist/lib/workspace-identity.js +8 -13
- package/dist/lib/workspace-retirement.d.ts +1 -1
- package/dist/lib/workspace-retirement.js +328 -140
- package/dist/lib/workspace-slots.js +8 -4
- package/dist/package.json +1 -1
- package/docs/architecture.md +31 -29
- package/docs/inbound.md +1 -1
- package/docs/multi-instance-bus.md +15 -3
- package/docs/outbound.md +1 -1
- package/docs/public-api.md +29 -1
- package/docs/ui-style.md +25 -8
- package/lib/activity-verbosity.ts +59 -82
- package/lib/activity.ts +146 -102
- package/lib/agent-messages.ts +12 -5
- package/lib/bindings.ts +389 -82
- package/lib/bus-api.ts +263 -102
- package/lib/bus-follower.ts +2440 -601
- package/lib/bus-leader.ts +2209 -1290
- package/lib/bus-transport.ts +46 -12
- package/lib/bus.ts +1673 -444
- package/lib/channel-posts.ts +848 -327
- package/lib/command-templates.ts +152 -265
- package/lib/commands.ts +2398 -555
- package/lib/config.ts +177 -170
- package/lib/delivery.ts +41 -29
- package/lib/extension.ts +1206 -433
- package/lib/generative-app-worker.mjs +19 -7
- package/lib/generative-apps.ts +324 -211
- package/lib/inbound.ts +95 -97
- package/lib/journal.ts +5311 -1763
- package/lib/keyboard.ts +1 -3
- package/lib/lifecycle.ts +128 -78
- package/lib/locks.ts +677 -203
- package/lib/logging.ts +147 -58
- package/lib/media.ts +82 -43
- package/lib/menu-model.ts +85 -18
- package/lib/menu-queue.ts +88 -129
- package/lib/menu-settings.ts +260 -155
- package/lib/menu-status.ts +20 -60
- package/lib/menu-thinking.ts +41 -56
- package/lib/menu.ts +112 -285
- package/lib/model.ts +8 -22
- package/lib/outbound-attachments.ts +156 -125
- package/lib/outbound-buttons.ts +76 -49
- package/lib/outbound-markup.ts +96 -94
- package/lib/outbound-voice.ts +33 -27
- package/lib/outbound.ts +128 -125
- package/lib/ownership.ts +19 -10
- package/lib/paths.ts +148 -49
- package/lib/pi.ts +35 -15
- package/lib/polling.ts +144 -147
- package/lib/preview.ts +93 -40
- package/lib/process-identity.ts +164 -0
- package/lib/prompts.ts +4 -11
- package/lib/queue.ts +516 -301
- package/lib/recovery.ts +50 -454
- package/lib/rendering.ts +1 -3
- package/lib/replies.ts +248 -209
- package/lib/routing.ts +8509 -2186
- package/lib/runtime.ts +1 -12
- package/lib/sections.ts +24 -89
- package/lib/setup.ts +1 -3
- package/lib/skills.ts +9 -4
- package/lib/status.ts +215 -110
- package/lib/sync.ts +448 -361
- package/lib/target.ts +22 -3
- package/lib/telegram-api.ts +302 -127
- package/lib/text-groups.ts +5 -39
- package/lib/thread-cleanup-manager.ts +833 -331
- package/lib/thread-display.ts +213 -97
- package/lib/thread-naming.ts +232 -87
- package/lib/thread-reconciler.ts +155 -72
- package/lib/threads.ts +5318 -1845
- package/lib/time-injection.ts +1 -4
- package/lib/turns.ts +15 -28
- package/lib/updates.ts +5184 -1612
- package/lib/voice.ts +7 -35
- package/lib/wire.ts +1 -1
- package/lib/workspace-admission.ts +996 -416
- package/lib/workspace-identity.ts +14 -17
- package/lib/workspace-retirement.ts +878 -376
- package/lib/workspace-slots.ts +22 -13
- package/package.json +1 -1
- package/scripts/check-downgrade.mjs +0 -472
- package/scripts/measure-workspace.mjs +0 -108
package/lib/keyboard.ts
CHANGED
package/lib/lifecycle.ts
CHANGED
|
@@ -6,10 +6,8 @@
|
|
|
6
6
|
*/
|
|
7
7
|
|
|
8
8
|
import { randomUUID } from "node:crypto";
|
|
9
|
-
|
|
9
|
+
|
|
10
10
|
import * as BusFollower from "./bus-follower.ts";
|
|
11
|
-
import * as Queue from "./queue.ts";
|
|
12
|
-
import * as TextGroups from "./text-groups.ts";
|
|
13
11
|
import type {
|
|
14
12
|
AgentEndEvent,
|
|
15
13
|
AgentSettledEvent,
|
|
@@ -31,24 +29,22 @@ import type {
|
|
|
31
29
|
UIPromptEndEvent,
|
|
32
30
|
UIPromptStartEvent,
|
|
33
31
|
} from "./pi.ts";
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
export function setResetTransportReplyDedup(fn: () => void): void {
|
|
38
|
-
resetTransportReplyDedupFn = fn;
|
|
39
|
-
}
|
|
32
|
+
import * as Queue from "./queue.ts";
|
|
33
|
+
import { formatTelegramConnectionFailure } from "./status.ts";
|
|
34
|
+
import * as TextGroups from "./text-groups.ts";
|
|
40
35
|
|
|
41
36
|
export function createAgentStartDedupHook(
|
|
42
37
|
inner: (event: AgentStartEvent, ctx: ExtensionContext) => Promise<void>,
|
|
38
|
+
resetReplyDedup: () => void,
|
|
43
39
|
schedulePublication?: (task: () => Promise<void>) => void,
|
|
44
40
|
): (event: AgentStartEvent, ctx: ExtensionContext) => Promise<void> {
|
|
45
41
|
return async (event, ctx) => {
|
|
46
|
-
|
|
47
|
-
if (
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
42
|
+
// A new turn must not erase the anchor of a final still ahead in the FIFO.
|
|
43
|
+
if (schedulePublication)
|
|
44
|
+
schedulePublication(async () => {
|
|
45
|
+
resetReplyDedup();
|
|
46
|
+
});
|
|
47
|
+
else resetReplyDedup();
|
|
52
48
|
return inner(event, ctx);
|
|
53
49
|
};
|
|
54
50
|
}
|
|
@@ -175,12 +171,18 @@ export interface TelegramConnectionHandoffStore {
|
|
|
175
171
|
}
|
|
176
172
|
const HANDOFF_KEY = Symbol.for("pi-telegram.connection-resume.v1");
|
|
177
173
|
function processHandoffStore(): TelegramConnectionHandoffStore {
|
|
178
|
-
const globals = globalThis as unknown as Record<
|
|
179
|
-
|
|
174
|
+
const globals = globalThis as unknown as Record<
|
|
175
|
+
symbol,
|
|
176
|
+
TelegramConnectionHandoffStore
|
|
177
|
+
>;
|
|
178
|
+
return (globals[HANDOFF_KEY] ??= {});
|
|
180
179
|
}
|
|
181
180
|
|
|
182
181
|
export interface TelegramConnectionLifecycle {
|
|
183
|
-
prepare(
|
|
182
|
+
prepare(
|
|
183
|
+
event: SessionStartEvent,
|
|
184
|
+
ctx: ExtensionContext,
|
|
185
|
+
): (() => void) | undefined;
|
|
184
186
|
onSessionShutdown(event: SessionShutdownEvent, ctx: ExtensionContext): void;
|
|
185
187
|
}
|
|
186
188
|
|
|
@@ -190,52 +192,81 @@ export function createTelegramConnectionLifecycle(deps: {
|
|
|
190
192
|
isCurrent(ctx: ExtensionContext): boolean;
|
|
191
193
|
getProfileName(): string | undefined;
|
|
192
194
|
isConnected(): boolean;
|
|
193
|
-
activateProfile(
|
|
195
|
+
activateProfile(
|
|
196
|
+
profileName: string | undefined,
|
|
197
|
+
isCurrent: () => boolean,
|
|
198
|
+
): Promise<boolean>;
|
|
194
199
|
start(ctx: ExtensionContext): Promise<{ ok: boolean; message?: string }>;
|
|
195
200
|
recordError(error: unknown): void;
|
|
196
201
|
}): TelegramConnectionLifecycle {
|
|
197
202
|
return {
|
|
198
203
|
onSessionShutdown(event, ctx) {
|
|
199
|
-
deps.intent.suspend({
|
|
200
|
-
|
|
201
|
-
|
|
204
|
+
deps.intent.suspend({
|
|
205
|
+
reason: event.reason,
|
|
206
|
+
cwd: ctx.cwd,
|
|
207
|
+
targetSessionFile: event.targetSessionFile,
|
|
208
|
+
connected: deps.isConnected(),
|
|
209
|
+
profileName: deps.getProfileName(),
|
|
210
|
+
});
|
|
202
211
|
},
|
|
203
212
|
prepare(event, ctx) {
|
|
204
|
-
const intent = deps.intent.resume({
|
|
205
|
-
|
|
213
|
+
const intent = deps.intent.resume({
|
|
214
|
+
reason: event.reason,
|
|
215
|
+
cwd: ctx.cwd,
|
|
216
|
+
sessionFile:
|
|
217
|
+
event.reason === "resume"
|
|
218
|
+
? ctx.sessionManager.getSessionFile()
|
|
219
|
+
: undefined,
|
|
220
|
+
});
|
|
206
221
|
if (!intent) return undefined;
|
|
207
222
|
const generation = deps.getGeneration();
|
|
208
|
-
const isCurrent = () =>
|
|
209
|
-
|
|
223
|
+
const isCurrent = () =>
|
|
224
|
+
deps.intent.isActive(intent.id) &&
|
|
225
|
+
generation === deps.getGeneration() &&
|
|
226
|
+
deps.isCurrent(ctx);
|
|
210
227
|
return () => {
|
|
211
228
|
// Startup remains extension-owned background work; no captured command ctx crosses resume.
|
|
212
229
|
void (async () => {
|
|
213
230
|
if (!isCurrent()) return;
|
|
214
|
-
if (!await deps.activateProfile(intent.profileName, isCurrent)) {
|
|
215
|
-
if (isCurrent())
|
|
231
|
+
if (!(await deps.activateProfile(intent.profileName, isCurrent))) {
|
|
232
|
+
if (isCurrent())
|
|
233
|
+
ctx.ui.notify(
|
|
234
|
+
"Telegram profile unavailable. Run /telegram-setup.",
|
|
235
|
+
"warning",
|
|
236
|
+
);
|
|
216
237
|
return;
|
|
217
238
|
}
|
|
218
239
|
if (!isCurrent()) return;
|
|
219
240
|
const result = await deps.start(ctx);
|
|
220
241
|
if (!isCurrent()) return;
|
|
221
242
|
if (!result.ok) {
|
|
222
|
-
deps.recordError(
|
|
223
|
-
|
|
243
|
+
deps.recordError(
|
|
244
|
+
new Error(result.message ?? "Telegram resume connection failed."),
|
|
245
|
+
);
|
|
246
|
+
ctx.ui.notify(
|
|
247
|
+
formatTelegramConnectionFailure(result.message),
|
|
248
|
+
"warning",
|
|
249
|
+
);
|
|
224
250
|
}
|
|
225
|
-
})()
|
|
226
|
-
|
|
227
|
-
|
|
228
|
-
|
|
251
|
+
})()
|
|
252
|
+
.catch((error) => {
|
|
253
|
+
deps.recordError(error);
|
|
254
|
+
if (isCurrent())
|
|
255
|
+
ctx.ui.notify(formatTelegramConnectionFailure(error), "warning");
|
|
256
|
+
})
|
|
257
|
+
.finally(() => deps.intent.finish(intent.id));
|
|
229
258
|
};
|
|
230
259
|
},
|
|
231
260
|
};
|
|
232
261
|
}
|
|
233
262
|
|
|
234
|
-
export function createTelegramConnectionIntentRuntime(
|
|
235
|
-
|
|
236
|
-
|
|
237
|
-
|
|
238
|
-
|
|
263
|
+
export function createTelegramConnectionIntentRuntime(
|
|
264
|
+
options: {
|
|
265
|
+
store?: TelegramConnectionHandoffStore;
|
|
266
|
+
now?: () => number;
|
|
267
|
+
pid?: number;
|
|
268
|
+
} = {},
|
|
269
|
+
) {
|
|
239
270
|
const store = options.store ?? processHandoffStore();
|
|
240
271
|
const now = options.now ?? Date.now;
|
|
241
272
|
const pid = options.pid ?? process.pid;
|
|
@@ -263,22 +294,45 @@ export function createTelegramConnectionIntentRuntime(options: {
|
|
|
263
294
|
connected: boolean;
|
|
264
295
|
profileName?: string;
|
|
265
296
|
}): void {
|
|
266
|
-
const intent =
|
|
267
|
-
|
|
268
|
-
|
|
297
|
+
const intent =
|
|
298
|
+
active ??
|
|
299
|
+
(input.connected
|
|
300
|
+
? { id: randomUUID(), cwd: input.cwd, profileName: input.profileName }
|
|
301
|
+
: undefined);
|
|
269
302
|
active = undefined;
|
|
270
|
-
store.pending =
|
|
271
|
-
|
|
272
|
-
|
|
273
|
-
|
|
303
|
+
store.pending =
|
|
304
|
+
input.reason === "resume" &&
|
|
305
|
+
input.targetSessionFile &&
|
|
306
|
+
intent?.cwd === input.cwd
|
|
307
|
+
? {
|
|
308
|
+
...intent,
|
|
309
|
+
pid,
|
|
310
|
+
targetSessionFile: input.targetSessionFile,
|
|
311
|
+
expiresAtMs: now() + 30_000,
|
|
312
|
+
}
|
|
313
|
+
: undefined;
|
|
274
314
|
},
|
|
275
|
-
resume(input: {
|
|
315
|
+
resume(input: {
|
|
316
|
+
reason: string;
|
|
317
|
+
cwd: string;
|
|
318
|
+
sessionFile?: string;
|
|
319
|
+
}): TelegramConnectionIntent | undefined {
|
|
276
320
|
const handoff = store.pending;
|
|
277
321
|
store.pending = undefined;
|
|
278
|
-
if (
|
|
279
|
-
|
|
280
|
-
|
|
281
|
-
|
|
322
|
+
if (
|
|
323
|
+
!handoff ||
|
|
324
|
+
handoff.pid !== pid ||
|
|
325
|
+
now() >= handoff.expiresAtMs ||
|
|
326
|
+
input.reason !== "resume" ||
|
|
327
|
+
input.cwd !== handoff.cwd ||
|
|
328
|
+
input.sessionFile !== handoff.targetSessionFile
|
|
329
|
+
)
|
|
330
|
+
return undefined;
|
|
331
|
+
active = {
|
|
332
|
+
id: randomUUID(),
|
|
333
|
+
cwd: handoff.cwd,
|
|
334
|
+
profileName: handoff.profileName,
|
|
335
|
+
};
|
|
282
336
|
return { ...active };
|
|
283
337
|
},
|
|
284
338
|
};
|
|
@@ -394,7 +448,9 @@ export interface TelegramBridgeSessionServiceRuntime {
|
|
|
394
448
|
capabilityMonitor: { start(ctx: ExtensionContext): void; stop(): void };
|
|
395
449
|
queueWatchdog: { start(ctx: ExtensionContext): void; stop(): void };
|
|
396
450
|
guestPlaceholder?: { stopAll(): void };
|
|
397
|
-
prepareThreadPreservationOnQuit?: (
|
|
451
|
+
prepareThreadPreservationOnQuit?: (
|
|
452
|
+
isSessionCurrent: () => boolean,
|
|
453
|
+
) => (() => Promise<void>) | undefined;
|
|
398
454
|
}
|
|
399
455
|
|
|
400
456
|
export interface TelegramBridgeSessionLifecycleAssemblyDeps<
|
|
@@ -482,7 +538,8 @@ export function createTelegramBridgeSessionLifecycleDeps<
|
|
|
482
538
|
capabilityMonitor: ports.services.capabilityMonitor,
|
|
483
539
|
queueWatchdog: ports.services.queueWatchdog,
|
|
484
540
|
guestPlaceholder: ports.services.guestPlaceholder,
|
|
485
|
-
prepareThreadPreservationOnQuit:
|
|
541
|
+
prepareThreadPreservationOnQuit:
|
|
542
|
+
ports.services.prepareThreadPreservationOnQuit,
|
|
486
543
|
},
|
|
487
544
|
};
|
|
488
545
|
}
|
|
@@ -530,9 +587,12 @@ export function createTelegramBridgeSessionLifecycleAssembly<
|
|
|
530
587
|
let preserveThread: (() => Promise<void>) | undefined;
|
|
531
588
|
if (event.reason === "quit") {
|
|
532
589
|
try {
|
|
533
|
-
preserveThread =
|
|
590
|
+
preserveThread =
|
|
591
|
+
deps.services.prepareThreadPreservationOnQuit?.(isCurrent);
|
|
534
592
|
} catch (error) {
|
|
535
|
-
deps.follower.recordRuntimeEvent("session", error, {
|
|
593
|
+
deps.follower.recordRuntimeEvent("session", error, {
|
|
594
|
+
phase: "preserve-thread-on-quit",
|
|
595
|
+
});
|
|
536
596
|
}
|
|
537
597
|
}
|
|
538
598
|
deps.services.guestPlaceholder?.stopAll();
|
|
@@ -547,7 +607,9 @@ export function createTelegramBridgeSessionLifecycleAssembly<
|
|
|
547
607
|
try {
|
|
548
608
|
await preserveThread?.();
|
|
549
609
|
} catch (error) {
|
|
550
|
-
deps.follower.recordRuntimeEvent("session", error, {
|
|
610
|
+
deps.follower.recordRuntimeEvent("session", error, {
|
|
611
|
+
phase: "preserve-thread-on-quit",
|
|
612
|
+
});
|
|
551
613
|
}
|
|
552
614
|
},
|
|
553
615
|
};
|
|
@@ -623,6 +685,13 @@ export function createTelegramCompactionObserverRuntime<TContext>(
|
|
|
623
685
|
clearTimer(fallbackTimer);
|
|
624
686
|
fallbackTimer = undefined;
|
|
625
687
|
};
|
|
688
|
+
// Stop only a typing loop this observer started; a pre-existing agent-owned loop is preserved.
|
|
689
|
+
const releaseCompactionPresence = (ctx: TContext): void => {
|
|
690
|
+
deps.setCompactionInProgress(false);
|
|
691
|
+
if (typingStartedByObserver) deps.stopTypingLoop?.();
|
|
692
|
+
typingStartedByObserver = false;
|
|
693
|
+
deps.updateStatus(ctx);
|
|
694
|
+
};
|
|
626
695
|
const requestDispatch = (): void => {
|
|
627
696
|
deps.requestDeferredDispatchNextQueuedTelegramTurn(
|
|
628
697
|
deps.dispatchNextQueuedTelegramTurn,
|
|
@@ -643,10 +712,7 @@ export function createTelegramCompactionObserverRuntime<TContext>(
|
|
|
643
712
|
observationGeneration += 1;
|
|
644
713
|
fallbackTimer = undefined;
|
|
645
714
|
if (deps.isContextActive && !deps.isContextActive(ctx)) return;
|
|
646
|
-
|
|
647
|
-
if (typingStartedByObserver) deps.stopTypingLoop?.();
|
|
648
|
-
typingStartedByObserver = false;
|
|
649
|
-
deps.updateStatus(ctx);
|
|
715
|
+
releaseCompactionPresence(ctx);
|
|
650
716
|
deps.recordRuntimeEvent?.(
|
|
651
717
|
"compact",
|
|
652
718
|
new Error("Compaction observer timed out"),
|
|
@@ -659,19 +725,13 @@ export function createTelegramCompactionObserverRuntime<TContext>(
|
|
|
659
725
|
onSessionCompact: (_event, ctx) => {
|
|
660
726
|
if (deps.isContextActive && !deps.isContextActive(ctx)) return;
|
|
661
727
|
clearFallbackTimer();
|
|
662
|
-
|
|
663
|
-
if (typingStartedByObserver) deps.stopTypingLoop?.();
|
|
664
|
-
typingStartedByObserver = false;
|
|
665
|
-
deps.updateStatus(ctx);
|
|
728
|
+
releaseCompactionPresence(ctx);
|
|
666
729
|
requestDispatch();
|
|
667
730
|
},
|
|
668
731
|
onSessionCompactFailed: (_event, ctx) => {
|
|
669
732
|
if (deps.isContextActive && !deps.isContextActive(ctx)) return;
|
|
670
733
|
clearFallbackTimer();
|
|
671
|
-
|
|
672
|
-
if (typingStartedByObserver) deps.stopTypingLoop?.();
|
|
673
|
-
typingStartedByObserver = false;
|
|
674
|
-
deps.updateStatus(ctx);
|
|
734
|
+
releaseCompactionPresence(ctx);
|
|
675
735
|
deps.onCompactionAbandoned?.();
|
|
676
736
|
requestDispatch();
|
|
677
737
|
},
|
|
@@ -730,16 +790,6 @@ export function createTelegramMessageActivityTypingHooks<
|
|
|
730
790
|
};
|
|
731
791
|
}
|
|
732
792
|
|
|
733
|
-
export function createDedupAgentStartHook(
|
|
734
|
-
dedup: { reset(): void },
|
|
735
|
-
inner: (event: AgentStartEvent, ctx: ExtensionContext) => Promise<void>,
|
|
736
|
-
): (event: AgentStartEvent, ctx: ExtensionContext) => Promise<void> {
|
|
737
|
-
return async (event, ctx) => {
|
|
738
|
-
dedup.reset();
|
|
739
|
-
await inner(event, ctx);
|
|
740
|
-
};
|
|
741
|
-
}
|
|
742
|
-
|
|
743
793
|
export interface TelegramExtraLifecycleHooks {
|
|
744
794
|
onSessionStart?: (
|
|
745
795
|
event: SessionStartEvent,
|