@eddyskywalker/dsh-chatgpt-subscription 0.12.2 → 0.12.4

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/lib/index.js CHANGED
@@ -21610,8 +21610,10 @@ function assertStreamComplete$3(state) {
21610
21610
  * - `INVALID_CREDENTIAL` — a rejected access token fails identically on every
21611
21611
  * attempt;
21612
21612
  * - `PROVIDER_ERROR` — a 400, a 401 that is really a plan-entitlement refusal,
21613
- * or a 403 quota limit. Retrying a quota that resets in hours only burns
21614
- * requests and delays the message the user needs to see;
21613
+ * or a 403 quota limit. Retrying a quota that resets in hours against the
21614
+ * SAME account only burns requests and delays the message the user needs to
21615
+ * see, so none of it is retried; a 403 limit still rotates to another account
21616
+ * when the pool holds one, which is a routing decision rather than a retry;
21615
21617
  * - `ABORTED` — the caller already cancelled.
21616
21618
  *
21617
21619
  * The DSH normal defaults would apply anyway; stating the values here pins them
@@ -21695,17 +21697,20 @@ function classifyKimiFailure(status, bodyText) {
21695
21697
  if (isHttpContextOverflow(status, bodyText)) return {
21696
21698
  code: CONTEXT_OVERFLOW_CODE,
21697
21699
  retryable: false,
21700
+ accountScoped: false,
21698
21701
  message: `${PROVIDER_NAME$3} context window exceeded: ${detail}`
21699
21702
  };
21700
21703
  if (status === 402) return {
21701
21704
  code: "SERVER",
21702
21705
  retryable: true,
21706
+ accountScoped: false,
21703
21707
  message: `${PROVIDER_NAME$3} could not verify the subscription tier (402). Retrying; if it persists, confirm the membership is active.${detail ? ` ${detail}` : ""}`
21704
21708
  };
21705
21709
  if (status === 401 || status === 403) {
21706
21710
  if (matchesAny$1(detail, ENTITLEMENT_PATTERNS)) return {
21707
21711
  code: "PROVIDER_ERROR",
21708
21712
  retryable: false,
21713
+ accountScoped: false,
21709
21714
  message: `${PROVIDER_NAME$3} refused this request for the current plan: ${detail || "the requested model or context is not included"}. Switch to a model the plan includes, lower the context-window override, or upgrade the subscription.`
21710
21715
  };
21711
21716
  if (status === 403) {
@@ -21713,12 +21718,14 @@ function classifyKimiFailure(status, bodyText) {
21713
21718
  return {
21714
21719
  code: "PROVIDER_ERROR",
21715
21720
  retryable: false,
21721
+ accountScoped: true,
21716
21722
  message: `${PROVIDER_NAME$3} blocked the request on an account limit (403): ${detail || (limitReached ? "the account limit was reached" : "the account refused the request")}. The quota refreshes on its own schedule — check the Kimi Code card in Settings for the reset time.`
21717
21723
  };
21718
21724
  }
21719
21725
  return {
21720
21726
  code: "INVALID_CREDENTIAL",
21721
21727
  retryable: false,
21728
+ accountScoped: false,
21722
21729
  message: `${PROVIDER_NAME$3} rejected the stored credential (401). Sign in again from Settings > Kimi Code.${detail ? ` ${detail}` : ""}`
21723
21730
  };
21724
21731
  }
@@ -21726,32 +21733,81 @@ function classifyKimiFailure(status, bodyText) {
21726
21733
  if (matchesAny$1(detail, QUOTA_EXHAUSTED_PATTERNS$1)) return {
21727
21734
  code: "PROVIDER_ERROR",
21728
21735
  retryable: false,
21736
+ accountScoped: true,
21729
21737
  message: `${PROVIDER_NAME$3} reports the account quota is exhausted: ${detail || "no remaining quota"}. Top up or wait for the window to reset.`
21730
21738
  };
21731
21739
  return {
21732
21740
  code: "RATE_LIMIT",
21733
21741
  retryable: true,
21742
+ accountScoped: false,
21734
21743
  message: `${PROVIDER_NAME$3} is rate limited or overloaded (429): ${detail || "too many requests"}. Retrying with backoff.`
21735
21744
  };
21736
21745
  }
21737
21746
  if (status >= 500) return {
21738
21747
  code: "SERVER",
21739
21748
  retryable: true,
21749
+ accountScoped: false,
21740
21750
  message: `${PROVIDER_NAME$3} upstream server error (${status}): ${detail || "the model provider is temporarily unavailable"}. Retrying with backoff.`
21741
21751
  };
21742
21752
  if (status === 400) return {
21743
21753
  code: "PROVIDER_ERROR",
21744
21754
  retryable: false,
21755
+ accountScoped: false,
21745
21756
  message: `${PROVIDER_NAME$3} rejected the request (400): ${detail || "the request was not accepted"}`
21746
21757
  };
21747
21758
  return {
21748
21759
  code: "PROVIDER_ERROR",
21749
21760
  retryable: false,
21761
+ accountScoped: false,
21750
21762
  message: `${PROVIDER_NAME$3} API error (${status}): ${detail || "No response"}`
21751
21763
  };
21752
21764
  }
21765
+ /** Numeric reset the service may ship as a field rather than in prose. */
21766
+ const RESET_FIELD_PATTERN = /"?reset[A-Za-z_]*"?\s*[:=]\s*"?(\d{9,16})"?/i;
21767
+ /** ISO instant quoted in prose, trusted only when it names its own zone. */
21768
+ const RESET_INSTANT_PATTERN = /\d{4}-\d{2}-\d{2}[T ]\d{2}:\d{2}(?::\d{2})?(?:\.\d+)?(?:Z|[+-]\d{2}:?\d{2})/;
21769
+ /** The window a billing-cycle refusal names; nothing shorter describes it. */
21770
+ const BILLING_CYCLE_PATTERN = /usage limit for this billing cycle/i;
21771
+ /**
21772
+ * How long one account stays out of rotation after it reports a spent limit.
21773
+ *
21774
+ * The reset instant is read from the body whenever the service states one — as a
21775
+ * numeric field, or as an instant carrying its own zone — and the length of the
21776
+ * window the service names is used otherwise. The zone is required for that
21777
+ * instant because an unqualified one is ambiguous, and a cooldown computed from
21778
+ * the wrong zone is either hours too long or already over; where the body is
21779
+ * ambiguous the window length is the honest answer.
21780
+ *
21781
+ * Both ends of the range are load-bearing. A reset instant barely in the future
21782
+ * would otherwise read as no cooldown at all and put the account straight back
21783
+ * into rotation to be refused again; and a reset instant already in the past
21784
+ * (a stale cache, a clock skew) falls back to the window length above rather
21785
+ * than to no cooldown at all.
21786
+ */
21787
+ function accountLimitCooldownMs(bodyText, now = Date.now()) {
21788
+ const field = bodyText.match(RESET_FIELD_PATTERN);
21789
+ const instant = bodyText.match(RESET_INSTANT_PATTERN);
21790
+ const resetsAt = field !== null ? parseTimestamp(Number(field[1])) : instant !== null ? Date.parse(instant[0].replace(" ", "T")) : null;
21791
+ if (resetsAt !== null && Number.isFinite(resetsAt) && resetsAt > now) return Math.min(Math.max(resetsAt - now, POOL_COOLDOWN_MS$2), MAX_ACCOUNT_LIMIT_COOLDOWN_MS);
21792
+ return BILLING_CYCLE_PATTERN.test(bodyText) ? BILLING_CYCLE_COOLDOWN_MS : ACCOUNT_LIMIT_COOLDOWN_MS;
21793
+ }
21753
21794
  /** Cooldown one rate-limited account takes when the provider states no delay. */
21754
21795
  const POOL_COOLDOWN_MS$2 = 15 * 6e4;
21796
+ /**
21797
+ * Fallback cooldown for an account whose usage window is spent.
21798
+ *
21799
+ * The service states the reset time only sometimes, so the fallback is the
21800
+ * window's own length. The 15 minutes a 429 gets would put the account back
21801
+ * into rotation four times inside the very window that just refused it.
21802
+ */
21803
+ const ACCOUNT_LIMIT_COOLDOWN_MS = 300 * 6e4;
21804
+ /**
21805
+ * A billing cycle is not a window: a 5-hour cooldown would spend a request every
21806
+ * five hours to learn an answer that changes at most once a month.
21807
+ */
21808
+ const BILLING_CYCLE_COOLDOWN_MS = 720 * 60 * 6e4;
21809
+ /** Ceiling, so a malformed reset time cannot park an account for years. */
21810
+ const MAX_ACCOUNT_LIMIT_COOLDOWN_MS = BILLING_CYCLE_COOLDOWN_MS;
21755
21811
  var KimiCodeAdapter = class extends LlmAdapter {
21756
21812
  store;
21757
21813
  modelSettings;
@@ -21936,11 +21992,15 @@ var KimiCodeAdapter = class extends LlmAdapter {
21936
21992
  if (pool !== null && accountId !== void 0) {
21937
21993
  const planScoped = response.status === 429 && matchesAny$1(detail, ENTITLEMENT_PATTERNS);
21938
21994
  if (response.status === 429 && !planScoped) {
21939
- await pool.markCooldown(accountId, after ?? POOL_COOLDOWN_MS$2, `${PROVIDER_NAME$3} 429`).catch(() => void 0);
21995
+ const cooldownMs = failure.accountScoped ? accountLimitCooldownMs(detail) : after ?? POOL_COOLDOWN_MS$2;
21996
+ await pool.markCooldown(accountId, cooldownMs, `${PROVIDER_NAME$3} 429`).catch(() => void 0);
21940
21997
  if (await pool.hasAnotherAvailableAccount(tried)) continue;
21941
21998
  } else if (failure.code === "INVALID_CREDENTIAL") {
21942
21999
  await pool.markAuthFailed(accountId, failure.message).catch(() => void 0);
21943
22000
  if (await pool.hasAnotherAvailableAccount(tried)) continue;
22001
+ } else if (failure.accountScoped) {
22002
+ await pool.markCooldown(accountId, accountLimitCooldownMs(detail), `${PROVIDER_NAME$3} 403`).catch(() => void 0);
22003
+ if (await pool.hasAnotherAvailableAccount(tried)) continue;
21944
22004
  }
21945
22005
  }
21946
22006
  throw new LlmError(failure.message, failure.code, {
@@ -43268,6 +43328,16 @@ function installRelayProbe(ctx, options) {
43268
43328
  * The guard rewrites nothing and appends nothing to the aborted attempt. Its
43269
43329
  * only model-visible input is the single resume message it queues afterwards,
43270
43330
  * on a fresh turn.
43331
+ *
43332
+ * Agent identity is read from the request, never remembered globally. The loop
43333
+ * stamps every request it builds with its `sessionId`, and `ctx.agents.get`
43334
+ * turns that back into the one Agent that owns the stream. Remembering "the
43335
+ * newest agent this process saw" instead was wrong twice over: a host runs one
43336
+ * Agent per session plus one per subagent, so the newest is usually a different
43337
+ * conversation, and `agent/created` fires once per Agent, so an Agent that
43338
+ * already existed when the guard installed was never reported at all. Both
43339
+ * cases cut the runaway and then resumed nothing, which reads to the user as a
43340
+ * conversation that simply stops mid-answer.
43271
43341
  */
43272
43342
  const DEFAULT_GUARD_OPTIONS = {
43273
43343
  windowChars: 4096,
@@ -43372,6 +43442,43 @@ function appendWindow(current, addition, limit) {
43372
43442
  const combined = current + addition;
43373
43443
  return combined.length > limit ? combined.slice(-limit) : combined;
43374
43444
  }
43445
+ /** An Agent's session identity as the plain string a request carries. */
43446
+ function agentId(raw) {
43447
+ const id = raw?.id;
43448
+ return typeof id === "string" ? id : void 0;
43449
+ }
43450
+ /**
43451
+ * The host's Agent registry, read defensively.
43452
+ *
43453
+ * A Cordis service that was never injected reads as undefined and a host
43454
+ * without the service at all must not fail this plugin's load, so both the
43455
+ * property read and the later lookup are guarded.
43456
+ */
43457
+ function agentRegistry(ctx) {
43458
+ try {
43459
+ const registry = ctx.agents;
43460
+ return typeof registry?.get === "function" ? registry : void 0;
43461
+ } catch {
43462
+ return;
43463
+ }
43464
+ }
43465
+ /**
43466
+ * Whether one request is a conversation call the guard may stop and resume.
43467
+ *
43468
+ * The loop marks its own requests, but that marker is reached through a named
43469
+ * export this plugin cannot assume on every generation it supports, so the
43470
+ * guard reads the request's own `purpose` field instead: compaction and
43471
+ * session-title calls are one-shot, own no turn to resume, and a truncated one
43472
+ * is a hard error rather than a runaway. A generation that predates the field
43473
+ * leaves it undefined, which is the pre-existing behaviour.
43474
+ */
43475
+ function conversationCall(request) {
43476
+ return request.purpose === void 0;
43477
+ }
43478
+ /** Error text for one warn line, without importing a generation-bound helper. */
43479
+ function describeError(error) {
43480
+ return error instanceof Error ? `${error.name}: ${error.message}` : String(error);
43481
+ }
43375
43482
  /**
43376
43483
  * Install the reasoning-collapse guard on a Context.
43377
43484
  *
@@ -43380,14 +43487,15 @@ function appendWindow(current, addition, limit) {
43380
43487
  * load.
43381
43488
  *
43382
43489
  * Resuming needs the live Agent for `cancel` and `steer`, and no supported
43383
- * generation hands the agent to `llm/stream`. `agent/created` reports it on
43384
- * every one of them, so the guard tracks the newest agent and keys the per-turn
43385
- * break budget on the request's own abort signal — which exists for a whole
43386
- * turn — rather than on the agent object.
43490
+ * generation hands the agent to `llm/stream`. The request does, though: every
43491
+ * request the loop builds carries its `sessionId`, so the guard resolves the
43492
+ * owning Agent per request through `ctx.agents.get`, falling back to the map
43493
+ * `agent/created` fills. The per-turn break budget stays keyed on the
43494
+ * request's own abort signal, which exists for a whole turn.
43387
43495
  *
43388
43496
  * @param ctx - plugin context.
43389
43497
  * @param options - see {@link GuardOptions}; validated fail-loud.
43390
- * @returns a disposer removing both listeners, or undefined when the host
43498
+ * @returns a disposer removing every listener, or undefined when the host
43391
43499
  * exposes no event bus.
43392
43500
  */
43393
43501
  function installReasoningCollapseGuard(ctx, options = {}) {
@@ -43395,11 +43503,38 @@ function installReasoningCollapseGuard(ctx, options = {}) {
43395
43503
  if (typeof ctx.on !== "function") return void 0;
43396
43504
  const watched = new Set(resolved.includeModels);
43397
43505
  const breakers = /* @__PURE__ */ new WeakMap();
43398
- let currentAgent;
43399
- const releaseAgent = ctx.on("agent/created", (payload) => {
43400
- currentAgent = payload.agent;
43506
+ const known = /* @__PURE__ */ new Map();
43507
+ const releaseCreated = ctx.on("agent/created", (payload) => {
43508
+ remember(payload.agent);
43509
+ });
43510
+ const releaseDisposed = ctx.on("agent/disposed", (payload) => {
43511
+ const id = agentId(payload.agent);
43512
+ if (id !== void 0) known.delete(id);
43401
43513
  });
43402
43514
  const releaseStream = ctx.on("llm/stream", guardStream, { global: true });
43515
+ function remember(raw) {
43516
+ const agent = raw;
43517
+ if (agent === void 0 || agent === null) return;
43518
+ const id = agentId(agent);
43519
+ if (id !== void 0) known.set(id, agent);
43520
+ }
43521
+ /**
43522
+ * The Agent that owns one guarded request, or undefined when this host
43523
+ * cannot name it.
43524
+ *
43525
+ * The registry is authoritative and is read first: it answers for an Agent
43526
+ * created before this guard was installed, which is exactly the Agent an
43527
+ * `agent/created` listener can never report. Falling back to the newest
43528
+ * Agent this process saw would cancel and resume a different conversation.
43529
+ */
43530
+ function resolveAgent(sessionId) {
43531
+ if (sessionId === void 0) return void 0;
43532
+ try {
43533
+ const registered = agentRegistry(ctx)?.get(sessionId);
43534
+ if (registered !== void 0 && registered !== null) return registered;
43535
+ } catch {}
43536
+ return known.get(sessionId);
43537
+ }
43403
43538
  function breakerFor(key) {
43404
43539
  let state = breakers.get(key);
43405
43540
  if (state === void 0) {
@@ -43419,27 +43554,36 @@ function installReasoningCollapseGuard(ctx, options = {}) {
43419
43554
  * steering submitted while a turn is still unwinding; by the time the
43420
43555
  * microtask runs the abort has settled, so the wake lands on a fresh turn that
43421
43556
  * inherits the kept inbox.
43557
+ *
43558
+ * With no Agent to address, the runaway is still cut — that half is the whole
43559
+ * point — and the log says so, because a break that cannot resume is
43560
+ * indistinguishable from a broken turn to the user.
43422
43561
  */
43423
- function breakOff(state, score) {
43562
+ function breakOff(state, score, agent, sessionId) {
43424
43563
  state.breaksThisTurn++;
43425
43564
  state.lastBreakAt = resolved.now();
43426
- ctx.logger?.warn(`reasoning-collapse-guard: stopped degenerate reasoning (score ${score.toFixed(3)}, break ${state.breaksThisTurn}/${resolved.maxBreaksPerTurn})`);
43427
- const agent = currentAgent;
43428
- agent?.cancel?.({
43565
+ ctx.logger?.warn(`reasoning-collapse-guard: stopped degenerate reasoning (score ${score.toFixed(3)}, break ${state.breaksThisTurn}/${resolved.maxBreaksPerTurn}, session ${sessionId ?? "unidentified"}${agent === void 0 ? ", no agent to resume" : ""})`);
43566
+ if (agent === void 0) return;
43567
+ agent.cancel?.({
43429
43568
  kind: "hook",
43430
43569
  reason: "reasoning-collapse-guard"
43431
43570
  }, { keepInbox: true });
43432
- if (agent === void 0 || state.resuming) return;
43571
+ if (agent.steer === void 0 || state.resuming) return;
43433
43572
  state.resuming = true;
43434
43573
  const text = state.breaksThisTurn >= 2 ? RESUME_HINT_STRICT : RESUME_HINT;
43435
43574
  queueMicrotask(() => {
43436
43575
  state.resuming = false;
43437
- agent.steer?.(createResumeMessage(text));
43576
+ try {
43577
+ agent.steer?.(createResumeMessage(text));
43578
+ } catch (error) {
43579
+ ctx.logger?.warn(`reasoning-collapse-guard: could not queue the resume: ${describeError(error)}`);
43580
+ }
43438
43581
  });
43439
43582
  }
43440
43583
  function guardStream(request, next) {
43441
43584
  const state = breakerFor(request.signal ?? STATIC_KEY);
43442
- if (state.exhausted || !watchedModel(request.model)) return next();
43585
+ if (state.exhausted || !watchedModel(request.model) || !conversationCall(request)) return next();
43586
+ const agent = resolveAgent(request.sessionId);
43443
43587
  async function* guarded() {
43444
43588
  let window = "";
43445
43589
  for await (const chunk of next()) {
@@ -43450,7 +43594,7 @@ function installReasoningCollapseGuard(ctx, options = {}) {
43450
43594
  const score = collapseScore(window, resolved.ngramSize);
43451
43595
  if (score >= resolved.threshold) if (state.breaksThisTurn >= resolved.maxBreaksPerTurn) state.exhausted = true;
43452
43596
  else {
43453
- breakOff(state, score);
43597
+ breakOff(state, score, agent, request.sessionId);
43454
43598
  return;
43455
43599
  }
43456
43600
  }
@@ -43462,7 +43606,9 @@ function installReasoningCollapseGuard(ctx, options = {}) {
43462
43606
  }
43463
43607
  return () => {
43464
43608
  releaseListener(releaseStream);
43465
- releaseListener(releaseAgent);
43609
+ releaseListener(releaseCreated);
43610
+ releaseListener(releaseDisposed);
43611
+ known.clear();
43466
43612
  };
43467
43613
  }
43468
43614
  /** Shared key for the rare request that carries no abort signal. */
@@ -28,8 +28,10 @@ import { KimiCodeAccountPool } from './account-pool.ts';
28
28
  * - `INVALID_CREDENTIAL` — a rejected access token fails identically on every
29
29
  * attempt;
30
30
  * - `PROVIDER_ERROR` — a 400, a 401 that is really a plan-entitlement refusal,
31
- * or a 403 quota limit. Retrying a quota that resets in hours only burns
32
- * requests and delays the message the user needs to see;
31
+ * or a 403 quota limit. Retrying a quota that resets in hours against the
32
+ * SAME account only burns requests and delays the message the user needs to
33
+ * see, so none of it is retried; a 403 limit still rotates to another account
34
+ * when the pool holds one, which is a routing decision rather than a retry;
33
35
  * - `ABORTED` — the caller already cancelled.
34
36
  *
35
37
  * The DSH normal defaults would apply anyway; stating the values here pins them
@@ -63,6 +65,22 @@ export interface KimiFailureClassification {
63
65
  message: string;
64
66
  /** True only when the failure is worth retrying. */
65
67
  retryable: boolean;
68
+ /**
69
+ * True when the refusal belongs to THIS account alone, so another pooled
70
+ * account may still serve the same request.
71
+ *
72
+ * A spent usage window is the case that matters, and this service reports it
73
+ * as a 403 — neither a bad credential nor retryable back-pressure, so nothing
74
+ * in the code or the message says "rotate". Asking the same account again
75
+ * cannot help; taking it out of rotation until its window resets lets the next
76
+ * account answer, and each account in the pool carries its own quota.
77
+ *
78
+ * False for every verdict that belongs to the request or to the plan: an
79
+ * entitlement refusal, a malformed body, ordinary overload. Rotating on one of
80
+ * those would spend every account in the pool to learn the same answer from
81
+ * each of them.
82
+ */
83
+ accountScoped: boolean;
66
84
  }
67
85
  /** Short, single-line excerpt of one error body, safe to show a user. */
68
86
  export declare function summarizeFailureBody(raw: string): string;
@@ -73,6 +91,23 @@ export declare function summarizeFailureBody(raw: string): string;
73
91
  * @param bodyText - raw response body, used to separate overloaded statuses.
74
92
  */
75
93
  export declare function classifyKimiFailure(status: number, bodyText: string): KimiFailureClassification;
94
+ /**
95
+ * How long one account stays out of rotation after it reports a spent limit.
96
+ *
97
+ * The reset instant is read from the body whenever the service states one — as a
98
+ * numeric field, or as an instant carrying its own zone — and the length of the
99
+ * window the service names is used otherwise. The zone is required for that
100
+ * instant because an unqualified one is ambiguous, and a cooldown computed from
101
+ * the wrong zone is either hours too long or already over; where the body is
102
+ * ambiguous the window length is the honest answer.
103
+ *
104
+ * Both ends of the range are load-bearing. A reset instant barely in the future
105
+ * would otherwise read as no cooldown at all and put the account straight back
106
+ * into rotation to be refused again; and a reset instant already in the past
107
+ * (a stale cache, a clock skew) falls back to the window length above rather
108
+ * than to no cooldown at all.
109
+ */
110
+ export declare function accountLimitCooldownMs(bodyText: string, now?: number): number;
76
111
  export interface KimiCodeAdapterOptions {
77
112
  fetchFn?: typeof fetch;
78
113
  attachments?: AttachmentImageReader;
@@ -1 +1 @@
1
- {"version":3,"file":"adapter.d.ts","sourceRoot":"","sources":["../../../../src/host/kimi-code/adapter.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"adapter.d.ts","sourceRoot":"","sources":["../../../../src/host/kimi-code/adapter.ts"],"names":[],"mappings":"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"}
@@ -29,11 +29,32 @@
29
29
  * The guard rewrites nothing and appends nothing to the aborted attempt. Its
30
30
  * only model-visible input is the single resume message it queues afterwards,
31
31
  * on a fresh turn.
32
+ *
33
+ * Agent identity is read from the request, never remembered globally. The loop
34
+ * stamps every request it builds with its `sessionId`, and `ctx.agents.get`
35
+ * turns that back into the one Agent that owns the stream. Remembering "the
36
+ * newest agent this process saw" instead was wrong twice over: a host runs one
37
+ * Agent per session plus one per subagent, so the newest is usually a different
38
+ * conversation, and `agent/created` fires once per Agent, so an Agent that
39
+ * already existed when the guard installed was never reported at all. Both
40
+ * cases cut the runaway and then resumed nothing, which reads to the user as a
41
+ * conversation that simply stops mid-answer.
42
+ */
43
+ /**
44
+ * The subset of `llm/stream` options this guard reads.
45
+ *
46
+ * `sessionId` is what binds a stream to the Agent that owns it, and
47
+ * `purpose` tells a conversation call from an auxiliary one (compaction,
48
+ * session title) that owns no turn to resume. Both are plain request fields:
49
+ * the guard adds no generation-bound named import to learn them.
32
50
  */
33
- /** The subset of `llm/stream` options this guard reads. */
34
51
  export interface GuardStreamOptions {
35
52
  readonly model?: string | undefined;
36
53
  readonly signal?: AbortSignal | undefined;
54
+ /** Stamped by the agent loop on every request it builds. */
55
+ readonly sessionId?: string | undefined;
56
+ /** Absent on an ordinary conversation request; set on an auxiliary call. */
57
+ readonly purpose?: string | undefined;
37
58
  }
38
59
  /** A chunk as it crosses the stream boundary; only the reasoning delta is read. */
39
60
  export interface GuardChunk {
@@ -42,6 +63,8 @@ export interface GuardChunk {
42
63
  }
43
64
  /** Live Agent methods the guard calls. Optional so an older shape stays loadable. */
44
65
  export interface GuardAgentLike {
66
+ /** The Agent's session identity — the same value the loop stamps on requests. */
67
+ readonly id?: unknown;
45
68
  cancel?(cause: {
46
69
  kind: 'hook';
47
70
  reason: string;
@@ -52,12 +75,12 @@ export interface GuardAgentLike {
52
75
  }
53
76
  /** The `llm/stream` waterfall listener the guard registers. */
54
77
  export type GuardStreamListener = (options: GuardStreamOptions, next: () => AsyncIterable<GuardChunk>) => AsyncIterable<GuardChunk>;
55
- /** The `agent/created` listener the guard registers. */
56
- export type GuardAgentCreatedListener = (payload: {
78
+ /** The `agent/created` / `agent/disposed` listener the guard registers. */
79
+ export type GuardAgentEventListener = (payload: {
57
80
  agent: unknown;
58
81
  }) => void;
59
82
  /** Either listener {@link ReasoningCollapseContext.on} accepts. */
60
- export type GuardListener = GuardStreamListener | GuardAgentCreatedListener;
83
+ export type GuardListener = GuardStreamListener | GuardAgentEventListener;
61
84
  /** Listener options accepted by the harness event bus. */
62
85
  export interface GuardListenerOptions {
63
86
  /** Receive the event regardless of context filter checks. */
@@ -68,10 +91,18 @@ export interface GuardListenerOptions {
68
91
  * every supported harness generation without importing generation-bound types.
69
92
  */
70
93
  export interface ReasoningCollapseContext {
71
- on?: (event: 'llm/stream' | 'agent/created', listener: GuardListener, options?: GuardListenerOptions) => unknown;
94
+ on?: (event: 'llm/stream' | 'agent/created' | 'agent/disposed', listener: GuardListener, options?: GuardListenerOptions) => unknown;
72
95
  logger?: {
73
96
  warn(message: string): void;
74
97
  } | undefined;
98
+ /**
99
+ * The harness Agent registry, read once so a guard installed after an Agent
100
+ * was created can still resolve it. A host without the service degrades to
101
+ * the `agent/created` map rather than failing this plugin's load.
102
+ */
103
+ readonly agents?: {
104
+ get(id: unknown): unknown;
105
+ } | undefined;
75
106
  }
76
107
  /** Configuration for {@link installReasoningCollapseGuard}. */
77
108
  export interface GuardOptions {
@@ -131,14 +162,15 @@ export declare const RESUME_HINT_STRICT: string;
131
162
  * load.
132
163
  *
133
164
  * Resuming needs the live Agent for `cancel` and `steer`, and no supported
134
- * generation hands the agent to `llm/stream`. `agent/created` reports it on
135
- * every one of them, so the guard tracks the newest agent and keys the per-turn
136
- * break budget on the request's own abort signal — which exists for a whole
137
- * turn — rather than on the agent object.
165
+ * generation hands the agent to `llm/stream`. The request does, though: every
166
+ * request the loop builds carries its `sessionId`, so the guard resolves the
167
+ * owning Agent per request through `ctx.agents.get`, falling back to the map
168
+ * `agent/created` fills. The per-turn break budget stays keyed on the
169
+ * request's own abort signal, which exists for a whole turn.
138
170
  *
139
171
  * @param ctx - plugin context.
140
172
  * @param options - see {@link GuardOptions}; validated fail-loud.
141
- * @returns a disposer removing both listeners, or undefined when the host
173
+ * @returns a disposer removing every listener, or undefined when the host
142
174
  * exposes no event bus.
143
175
  */
144
176
  export declare function installReasoningCollapseGuard(ctx: ReasoningCollapseContext, options?: GuardOptions): (() => void) | undefined;
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../../src/host/reasoning-collapse-guard/index.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../../src/host/reasoning-collapse-guard/index.ts"],"names":[],"mappings":"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"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@eddyskywalker/dsh-chatgpt-subscription",
3
- "version": "0.12.2",
3
+ "version": "0.12.4",
4
4
  "description": "DSH provider plugin for Codex access through a ChatGPT subscription.",
5
5
  "author": {
6
6
  "name": "eddyskywalker",