@wrongstack/core 0.63.4 → 0.66.13

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 (57) hide show
  1. package/dist/{agent-bridge-B5rxWrg3.d.ts → agent-bridge-D-j6OOBT.d.ts} +1 -1
  2. package/dist/agent-subagent-runner-DRZ9-NnR.d.ts +1042 -0
  3. package/dist/{compactor-0vjZ8KTk.d.ts → compactor-D_ExJajC.d.ts} +1 -1
  4. package/dist/{config-BdDuaZmB.d.ts → config--86aHSln.d.ts} +1 -1
  5. package/dist/{context-iFMEO2rN.d.ts → context-y87Jc5ei.d.ts} +3 -3
  6. package/dist/coordination/index.d.ts +12 -12
  7. package/dist/coordination/index.js +87 -69
  8. package/dist/coordination/index.js.map +1 -1
  9. package/dist/defaults/index.d.ts +22 -22
  10. package/dist/defaults/index.js +113 -84
  11. package/dist/defaults/index.js.map +1 -1
  12. package/dist/{events-k8CHjcrN.d.ts → events-CIplI98R.d.ts} +1 -1
  13. package/dist/execution/index.d.ts +16 -385
  14. package/dist/execution/index.js +59 -51
  15. package/dist/execution/index.js.map +1 -1
  16. package/dist/extension/index.d.ts +6 -6
  17. package/dist/goal-store-C7jcumEh.d.ts +96 -0
  18. package/dist/{index-Bc6BiP5q.d.ts → index-DKUvyTvV.d.ts} +28 -442
  19. package/dist/{index-CWdW_CJt.d.ts → index-b5uhfTSl.d.ts} +8 -8
  20. package/dist/index.d.ts +34 -32
  21. package/dist/index.js +647 -677
  22. package/dist/index.js.map +1 -1
  23. package/dist/infrastructure/index.d.ts +6 -6
  24. package/dist/kernel/index.d.ts +9 -9
  25. package/dist/{mcp-servers-CwqQDMYy.d.ts → mcp-servers-DwoNBf6r.d.ts} +3 -3
  26. package/dist/models/index.d.ts +2 -2
  27. package/dist/{multi-agent-coordinator-CNUJYq7U.d.ts → multi-agent-coordinator-CWnH-CiX.d.ts} +10 -2
  28. package/dist/{null-fleet-bus-DRoJ0uOY.d.ts → null-fleet-bus-VApKRxcp.d.ts} +6 -7
  29. package/dist/observability/index.d.ts +2 -2
  30. package/dist/parallel-eternal-engine-0UwotoSx.d.ts +483 -0
  31. package/dist/{path-resolver-C5sPVne8.d.ts → path-resolver-DVkEcIw8.d.ts} +2 -2
  32. package/dist/{permission-Ld-i5ugf.d.ts → permission-C1A5whY5.d.ts} +5 -1
  33. package/dist/{permission-policy-CL-mPufp.d.ts → permission-policy-B2dK-T5N.d.ts} +19 -5
  34. package/dist/{plan-templates-ThBHOjaM.d.ts → plan-templates-Bprrzhbu.d.ts} +4 -4
  35. package/dist/{provider-runner-DJQa211J.d.ts → provider-runner-mXvXGSIw.d.ts} +3 -3
  36. package/dist/{retry-policy-BfBScewS.d.ts → retry-policy-CG3qvH_e.d.ts} +1 -1
  37. package/dist/sdd/index.d.ts +8 -8
  38. package/dist/sdd/index.js +58 -51
  39. package/dist/sdd/index.js.map +1 -1
  40. package/dist/security/index.d.ts +3 -3
  41. package/dist/security/index.js +31 -22
  42. package/dist/security/index.js.map +1 -1
  43. package/dist/{selector-DxhW7ML3.d.ts → selector-RvBR_YRW.d.ts} +1 -1
  44. package/dist/session-event-bridge-CDHxcmQU.d.ts +93 -0
  45. package/dist/{session-reader-q2ThszgG.d.ts → session-reader-BIpwM60D.d.ts} +1 -1
  46. package/dist/storage/index.d.ts +7 -6
  47. package/dist/{system-prompt-7LHyBbIf.d.ts → system-prompt-b61lOd49.d.ts} +2 -2
  48. package/dist/types/index.d.ts +23 -14
  49. package/dist/types/index.js.map +1 -1
  50. package/dist/utils/index.d.ts +2 -2
  51. package/dist/utils/index.js.map +1 -1
  52. package/package.json +1 -1
  53. package/skills/multi-agent/SKILL.md +0 -2
  54. package/dist/agent-subagent-runner-Zc3f37Sg.d.ts +0 -182
  55. package/dist/goal-store-iHltMi5n.d.ts +0 -188
  56. package/dist/multi-agent-SASYOrWA.d.ts +0 -554
  57. package/dist/tool-executor-CIjpGaRA.d.ts +0 -111
@@ -1,4 +1,4 @@
1
- import { $ as Usage, d as Context, X as ToolProgressEvent, Q as Tool } from './context-iFMEO2rN.js';
1
+ import { $ as Usage, d as Context, X as ToolProgressEvent, Q as Tool } from './context-y87Jc5ei.js';
2
2
 
3
3
  /**
4
4
  * Brain coordination primitives.
@@ -1,24 +1,24 @@
1
- export { C as CompactorOptions, a as DefaultErrorHandler, b as DefaultRetryPolicy, H as HybridCompactor, T as ToolExecutor } from '../tool-executor-CIjpGaRA.js';
2
- import { m as Provider, d as Context } from '../context-iFMEO2rN.js';
3
- import { a as Compactor, C as CompactReport } from '../compactor-0vjZ8KTk.js';
4
- import { M as MessageSelector } from '../selector-DxhW7ML3.js';
5
- import { E as EventBus } from '../events-k8CHjcrN.js';
6
- import { b as MiddlewareHandler } from '../system-prompt-7LHyBbIf.js';
7
- import { a as SessionEventBridge, J as JournalEntry } from '../goal-store-iHltMi5n.js';
8
- import { e as ContextWindowAggressiveOn, i as ContextWindowPolicy } from '../config-BdDuaZmB.js';
9
- import { c as Agent, R as RunResult, C as SystemPromptContributor } from '../index-Bc6BiP5q.js';
10
- import { D as DoneCondition } from '../multi-agent-SASYOrWA.js';
11
- import { A as AgentFactory } from '../agent-subagent-runner-Zc3f37Sg.js';
12
- import { f as DispatchClassifier, d as DefaultMultiAgentCoordinator } from '../multi-agent-coordinator-CNUJYq7U.js';
1
+ export { C as CompactorOptions, a as DefaultErrorHandler, b as DefaultRetryPolicy, E as EternalAutonomyEngine, c as EternalAutonomyOptions, d as EternalEngineState, H as HybridCompactor, I as IterationStage, P as ParallelEngineState, e as ParallelEternalEngine, f as ParallelEternalOptions, g as ParallelIterationStage, T as ToolExecutor } from '../parallel-eternal-engine-0UwotoSx.js';
2
+ import { m as Provider, d as Context } from '../context-y87Jc5ei.js';
3
+ import { a as Compactor, C as CompactReport } from '../compactor-D_ExJajC.js';
4
+ import { M as MessageSelector } from '../selector-RvBR_YRW.js';
5
+ import { E as EventBus } from '../events-CIplI98R.js';
6
+ import { b as MiddlewareHandler } from '../system-prompt-b61lOd49.js';
7
+ import { a as SessionEventBridge } from '../session-event-bridge-CDHxcmQU.js';
8
+ import { e as ContextWindowAggressiveOn, i as ContextWindowPolicy } from '../config--86aHSln.js';
9
+ import { A as Agent, D as DoneCondition } from '../agent-subagent-runner-DRZ9-NnR.js';
10
+ import { R as RunResult, S as SystemPromptContributor } from '../index-DKUvyTvV.js';
13
11
  import { a as SkillLoader, b as SkillManifest, S as SkillEntry } from '../skill-CxuWrsKK.js';
14
12
  import { a as WstackPaths } from '../wstack-paths-eMXnY1_X.js';
15
- import '../retry-policy-BfBScewS.js';
13
+ import '../retry-policy-CG3qvH_e.js';
16
14
  import '../models-registry-BcYJDKLm.js';
15
+ import '../goal-store-C7jcumEh.js';
16
+ import '../multi-agent-coordinator-CWnH-CiX.js';
17
+ import 'node:events';
17
18
  import '../logger-DDd5C--Z.js';
18
19
  import '../observability-BhnVLBLS.js';
20
+ import '../permission-C1A5whY5.js';
19
21
  import '../secret-scrubber-3MHDDAtm.js';
20
- import '../permission-Ld-i5ugf.js';
21
- import 'node:events';
22
22
 
23
23
  interface SkillLoaderOptions {
24
24
  paths: WstackPaths;
@@ -316,375 +316,6 @@ declare class AutonomousRunner {
316
316
  stop(): void;
317
317
  }
318
318
 
319
- /**
320
- * Sense-decide-execute-reflect loop on top of a long-running Goal.
321
- *
322
- * Each iteration:
323
- * 1. Sense — read goal, pending todos, `git status --porcelain`.
324
- * 2. Decide — pick a source (todo / git / brainstorm) and a task.
325
- * 3. Execute — single agent.run with a directive prompt.
326
- * 4. Reflect — append a journal entry, persist state to disk.
327
- *
328
- * The loop runs forever until `stop()` is called externally (REPL SIGINT
329
- * handler, /autonomy stop). No internal time/cost cap by design — the
330
- * user wants "sittin sene". Failures are logged and the loop continues
331
- * with a different source on the next tick.
332
- */
333
- interface EternalAutonomyOptions {
334
- agent: Agent;
335
- projectRoot: string;
336
- /**
337
- * Per-iteration agent timeout. Defaults to 5 minutes. A single hung
338
- * provider call should not freeze the whole eternal loop.
339
- */
340
- iterationTimeoutMs?: number;
341
- /**
342
- * Maximum number of internal agent.run iterations the engine grants per
343
- * eternal-loop tick. The engine sets `autonomousContinue: true` so the
344
- * agent can run multi-step tasks end-to-end within one tick instead of
345
- * bouncing back to the engine after every single tool call. Default 500.
346
- * Previous 50 was far too low — agents hit the limit and restart constantly.
347
- */
348
- iterationMaxAgentSteps?: number;
349
- /**
350
- * Minimum sleep between iterations. Defaults to 1 s — enough for
351
- * SIGINT handlers to fire mid-loop without pegging a core when the
352
- * provider is being rate-limited.
353
- */
354
- cycleGapMs?: number;
355
- /**
356
- * Maximum consecutive failures before the source rotation forces a
357
- * brainstorm cycle. Default 3. Acts as a soft-recovery, not a stop.
358
- */
359
- failureBudget?: number;
360
- /**
361
- * Per-todo failed-attempt ceiling. When the engine picks the same todo
362
- * and the iteration fails this many times in total, the todo is taken
363
- * out of rotation (engine prefers other sources) until it changes
364
- * status. Default 3. Prevents the loop from spinning forever on one
365
- * stuck task.
366
- */
367
- todoMaxAttempts?: number;
368
- /**
369
- * Consecutive brainstorm-DONE responses required to consider the goal
370
- * complete and stop the engine. When the LLM's brainstorm step keeps
371
- * answering `DONE`, the engine treats that as "no more work" and, after
372
- * this many in a row, marks the goal as completed instead of sleeping
373
- * forever. Default 3.
374
- */
375
- brainstormDoneStopThreshold?: number;
376
- /** Side-channel notifications (logging, UI updates). */
377
- onIteration?: (entry: JournalEntry) => void;
378
- onError?: (err: Error, iteration: number) => void;
379
- /**
380
- * Per-iteration phase notifications for live UI updates (TUI status bar,
381
- * etc.). Fires at each major stage transition: idle → decide → execute →
382
- * reflect → (sleep | paused | stopped). Fire-and-forget — the engine
383
- * does not await the callback.
384
- */
385
- onStage?: (stage: IterationStage) => void;
386
- /**
387
- * Optional injected git status reader — production code uses git, tests
388
- * stub this out so they don't shell out.
389
- */
390
- gitStatusReader?: () => Promise<string>;
391
- /**
392
- * Optional clock — tests stub for deterministic timestamps.
393
- */
394
- now?: () => Date;
395
- /**
396
- * Optional compactor. When provided, the engine runs compaction every
397
- * `compactEveryNIterations` iterations to keep the agent's message
398
- * history under control during multi-day eternal loops. Without
399
- * compaction, an infinite loop will eventually overflow the provider's
400
- * context window and start failing.
401
- */
402
- compactor?: Compactor;
403
- /** How many iterations between compaction calls. Default 25. */
404
- compactEveryNIterations?: number;
405
- /**
406
- * Aggressive compaction threshold. When ctx token usage exceeds this
407
- * fraction of `maxContextTokens`, compaction runs in aggressive mode
408
- * regardless of the iteration cadence. 0.85 by default.
409
- */
410
- aggressiveCompactRatio?: number;
411
- /**
412
- * Model's max context window in tokens. When set, the engine watches
413
- * `currentRequestTokens()` against this and triggers aggressive compact
414
- * before the next iteration would overflow. Omit to disable threshold
415
- * checks (iteration cadence still applies).
416
- */
417
- maxContextTokens?: number;
418
- /**
419
- * Base delay (ms) for the first transient-error backoff. Subsequent
420
- * transient failures double this, capped at `transientBackoffMaxMs`.
421
- * Default 2_000.
422
- *
423
- * "Transient" means the underlying error is recoverable per
424
- * `WrongStackError.recoverable` (ProviderError sets this for 429/529/5xx
425
- * /network errors). Permanent errors (auth/invalid request) skip the
426
- * backoff and count toward `failureBudget` like before — backing off
427
- * on a permanent failure is wasted time.
428
- */
429
- transientBackoffBaseMs?: number;
430
- /** Ceiling for the exponential backoff. Default 60_000 (60 s). */
431
- transientBackoffMaxMs?: number;
432
- /** Called when the eternal loop stops for any reason (manual stop, goal complete, etc.). */
433
- onEternalStop?: () => void;
434
- }
435
- type EternalEngineState = 'idle' | 'running' | 'stopped';
436
- /**
437
- * Per-iteration phase emitted via `onStage` so UIs can render the
438
- * engine's live location in the sense-decide-execute-reflect loop.
439
- */
440
- type IterationStage = {
441
- phase: 'idle';
442
- } | {
443
- phase: 'decide';
444
- reason: string;
445
- } | {
446
- phase: 'execute';
447
- task: string;
448
- } | {
449
- phase: 'reflect';
450
- status: 'success' | 'failure' | 'aborted' | 'skipped';
451
- note?: string;
452
- } | {
453
- phase: 'sleep';
454
- ms: number;
455
- } | {
456
- phase: 'paused';
457
- } | {
458
- phase: 'stopped';
459
- } | {
460
- phase: 'error';
461
- message: string;
462
- };
463
- declare class EternalAutonomyEngine {
464
- private readonly opts;
465
- private state;
466
- private stopRequested;
467
- private consecutiveFailures;
468
- private consecutiveBrainstormDone;
469
- /**
470
- * Count of consecutive transient (recoverable) provider failures. Drives
471
- * the exponential backoff between iterations. Reset on the first
472
- * successful iteration so a single bad afternoon doesn't permanently
473
- * slow the loop down.
474
- */
475
- private consecutiveTransientRetries;
476
- private currentCtrl;
477
- private iterationsSinceCompact;
478
- private readonly goalPath;
479
- constructor(opts: EternalAutonomyOptions);
480
- /** Current engine state — readable for UIs. */
481
- get currentState(): EternalEngineState;
482
- /** Synchronously request stop. Resolves once the running iteration aborts. */
483
- stop(): void;
484
- /**
485
- * Mark the engine as 'running' on disk + reset stop state so a new
486
- * batch of `runOneIteration()` calls can proceed. Called by the REPL
487
- * when the user invokes `/autonomy eternal`. Idempotent.
488
- */
489
- prime(): Promise<void>;
490
- /**
491
- * Main loop. Returns when stop() is called or the goal file is removed.
492
- * Does NOT throw — every iteration is wrapped to keep the loop alive.
493
- */
494
- run(): Promise<void>;
495
- /**
496
- * Execute a single sense-decide-execute-reflect cycle.
497
- * Returns true on success, false on handled failure / no-op.
498
- *
499
- * Exposed publicly so the REPL can pace iterations from its main loop
500
- * — running the engine and the REPL as a single sequential consumer of
501
- * `agent.run()` avoids race conditions on the shared Context.
502
- */
503
- runOneIteration(): Promise<boolean>;
504
- /**
505
- * Run compaction when either trigger fires:
506
- * - We've done >= compactEveryNIterations since the last compact.
507
- * - Current request tokens exceed aggressiveCompactRatio * maxContext.
508
- *
509
- * The second check uses *aggressive* mode to free more headroom; the
510
- * cadence check uses non-aggressive (cheaper).
511
- */
512
- private maybeCompact;
513
- /**
514
- * Hybrid idea source.
515
- * 1. Pending todos on the agent's context.
516
- * 2. Dirty git working tree → propose a "review and finish this" task.
517
- * 3. Otherwise: brainstorm via the LLM against the goal.
518
- *
519
- * After failureBudget consecutive failures, force brainstorm so the
520
- * engine doesn't loop on the same broken todo or stuck git state.
521
- */
522
- private decide;
523
- private pickPendingTodo;
524
- private pickGitTask;
525
- private readGitStatus;
526
- private brainstormTask;
527
- private buildDirective;
528
- /**
529
- * Exponential backoff for transient provider errors. `2^N * base`
530
- * capped at `transientBackoffMaxMs`. Zero base disables backoff.
531
- * Public-private to keep `runOneIteration` readable; the value is
532
- * recomputed each call from the current retry count, so callers
533
- * don't have to track state.
534
- */
535
- private computeTransientBackoffMs;
536
- /**
537
- * Sleep that wakes early if `stopRequested` flips. Polls every 250 ms
538
- * so SIGINT / `/autonomy stop` can land in the middle of a long
539
- * backoff instead of waiting up to a minute for the timer.
540
- */
541
- private sleepInterruptible;
542
- private appendIterationEntry;
543
- /**
544
- * Persistent per-todo failure counter. Skipped silently when the goal
545
- * file has been removed (graceful clear). Each non-success iteration
546
- * against a todo source bumps the counter by 1; `pickPendingTodo` reads
547
- * the counter to rotate past stuck todos once they cross `todoMaxAttempts`.
548
- */
549
- private bumpTodoAttempt;
550
- /**
551
- * Flip the mission to `completed` and journal it. Called from two
552
- * paths: (a) `[GOAL_COMPLETE]` marker in a successful iteration's
553
- * finalText, (b) `brainstorm` returning DONE consecutively past the
554
- * configured threshold. Idempotent — re-entry is a no-op once the
555
- * goal is already `completed`.
556
- */
557
- private markGoalCompleted;
558
- /**
559
- * Manually clear the goal — equivalent to `/goal clear` typed by the user.
560
- * Sets goalState to `abandoned`, removes the goal file, and fires
561
- * `onEternalStop` so the REPL returns to normal mode.
562
- */
563
- private clearGoalManually;
564
- private appendFailure;
565
- private persistEngineState;
566
- }
567
-
568
- type ParallelEngineState = 'idle' | 'running' | 'stopped';
569
- type ParallelIterationStage = {
570
- phase: 'idle';
571
- } | {
572
- phase: 'decompose';
573
- } | {
574
- phase: 'fanout';
575
- slots: number;
576
- } | {
577
- phase: 'await';
578
- taskIds: string[];
579
- } | {
580
- phase: 'aggregate';
581
- successCount: number;
582
- total: number;
583
- goalComplete: boolean;
584
- } | {
585
- phase: 'sleep';
586
- ms: number;
587
- } | {
588
- phase: 'stopped';
589
- } | {
590
- phase: 'error';
591
- message: string;
592
- };
593
- interface ParallelEternalOptions {
594
- /** The coordinating agent — NOT a subagent. Owns container/tools/providers. */
595
- agent: Agent;
596
- /** Project root (used for goal.json path). */
597
- projectRoot: string;
598
- /**
599
- * Override the resolved goal.json path. Defaults to
600
- * `goalFilePath(projectRoot)` (a hashed location under the home dir).
601
- * Primarily for tests that want an isolated goal file under a temp dir.
602
- */
603
- goalPath?: string;
604
- /**
605
- * Number of parallel subagent slots per tick.
606
- * Default: 4. Range 1–16; values >8 are for high-throughput machines.
607
- */
608
- parallelSlots?: number;
609
- /** Per-subagent default timeout in ms. Default: 300_000 (5 min). */
610
- iterationTimeoutMs?: number;
611
- onIteration?: (entry: JournalEntry) => void;
612
- onError?: (err: Error, iteration: number) => void;
613
- /** Per-tick phase notifications for live UI/status updates. */
614
- onStage?: (stage: ParallelIterationStage) => void;
615
- gitStatusReader?: () => Promise<string>;
616
- now?: () => Date;
617
- compactor?: Compactor;
618
- compactEveryNIterations?: number;
619
- aggressiveCompactRatio?: number;
620
- maxContextTokens?: number;
621
- /** Override the default agent factory (uses main agent if not provided). */
622
- subagentFactory?: AgentFactory;
623
- /**
624
- * Route each decomposed slot task to the best-fit catalog agent via the
625
- * smart dispatcher (heuristic keyword scoring). When enabled (default), each
626
- * slot spawns in-role — the role's budget tier applies and a persona line is
627
- * injected into the task — instead of as a faceless generic worker. Set
628
- * false to keep the legacy generic spawn.
629
- */
630
- dispatch?: boolean;
631
- /**
632
- * Optional LLM fallback for ambiguous tasks. Passed straight to
633
- * `dispatchAgent`; when omitted, routing is pure heuristic (instant, no
634
- * provider call — preferred for a continuously-ticking autonomous loop).
635
- */
636
- dispatchClassifier?: DispatchClassifier;
637
- }
638
- /**
639
- * Sense → Decide → Fan-out (4–8 parallel agents) → Aggregate → Loop.
640
- *
641
- * Each tick:
642
- * 1. Sense — load goal, todos, git status
643
- * 2. Decide — decompose goal into N parallel sub-tasks
644
- * 3. Fan-out — spawn N subagents simultaneously, await all
645
- * 4. Aggregate — write journal, update todos, check [GOAL_COMPLETE]
646
- * 5. Loop — continue until stop() or mission complete
647
- *
648
- * Uses DefaultMultiAgentCoordinator + AgentSubagentRunner for subagent lifecycle.
649
- */
650
- declare class ParallelEternalEngine {
651
- private readonly opts;
652
- private state;
653
- private stopRequested;
654
- private iterationsSinceCompact;
655
- private iterations;
656
- private consecutiveFailures;
657
- private readonly goalPath;
658
- private readonly slots;
659
- private readonly timeoutMs;
660
- private coordinator;
661
- private agentFactory;
662
- private readonly dispatchEnabled;
663
- private readonly dispatchClassifier?;
664
- constructor(opts: ParallelEternalOptions);
665
- get currentState(): ParallelEngineState;
666
- /**
667
- * Get the underlying coordinator for stats/monitoring.
668
- */
669
- getCoordinator(): DefaultMultiAgentCoordinator | null;
670
- stop(): void;
671
- prime(): Promise<void>;
672
- run(): Promise<void>;
673
- /**
674
- * Execute one tick: decompose → fan-out → aggregate → compact.
675
- * Called by the REPL in its main loop (REPL drives, engine is stateless per tick).
676
- */
677
- runOneIteration(): Promise<boolean>;
678
- private fanOut;
679
- private decomposeGoal;
680
- private readGitStatus;
681
- private brainstormSubtasks;
682
- private maybeCompact;
683
- private appendIterationEntry;
684
- private appendFailure;
685
- private persistState;
686
- }
687
-
688
319
  /**
689
320
  * System-prompt contributor that surfaces eternal-autonomy state to the
690
321
  * model on every turn.
@@ -754,4 +385,4 @@ declare function makeAutonomyPromptContributor(opts: AutonomyPromptContributorOp
754
385
  */
755
386
  declare function buildGoalPreamble(goal: string): string;
756
387
 
757
- export { AutoCompactionMiddleware, AutonomousRunner, type AutonomousRunnerOptions, type AutonomyPromptContributorOptions, DefaultSkillLoader, type DoneCheckResult, DoneConditionChecker, EternalAutonomyEngine, type EternalAutonomyOptions, type EternalEngineState, IntelligentCompactor, type IntelligentCompactorOptions, type IterationStage, type ParallelEngineState, ParallelEternalEngine, type ParallelEternalOptions, type ParallelIterationStage, SelectiveCompactor, type SelectiveCompactorOptions, type SkillLoaderOptions, buildGoalPreamble, makeAutonomyPromptContributor };
388
+ export { AutoCompactionMiddleware, AutonomousRunner, type AutonomousRunnerOptions, type AutonomyPromptContributorOptions, DefaultSkillLoader, type DoneCheckResult, DoneConditionChecker, IntelligentCompactor, type IntelligentCompactorOptions, SelectiveCompactor, type SelectiveCompactorOptions, type SkillLoaderOptions, buildGoalPreamble, makeAutonomyPromptContributor };
@@ -3014,15 +3014,22 @@ var SubagentBudget = class _SubagentBudget {
3014
3014
  void this.checkLimits();
3015
3015
  }
3016
3016
  /**
3017
- * Wall-clock budget check. Unlike other limits, timeout is always a hard stop
3018
- * wall-clock time cannot be "extended" by the coordinator, so it throws
3019
- * synchronously rather than entering the negotiation flow.
3017
+ * Wall-clock / idle budget check. Delegates to `checkLimits(elapsed)`, so
3018
+ * `timeout` and `idle_timeout` follow the SAME negotiation path as the other
3019
+ * kinds they are NOT a special-cased hard stop. This is deliberate: a
3020
+ * heartbeat-aware policy (see `attachAutoExtend` and `CollabSession`) grants
3021
+ * a timeout extension only while the agent is making progress and denies it
3022
+ * once the agent is genuinely stuck, which is safer than an unconditional
3023
+ * hard kill of a long-but-working agent. The runner translates the resulting
3024
+ * `BudgetThresholdSignal` decision (`extend` → patch limits in place,
3025
+ * `stop` → abort) just like every other kind.
3020
3026
  *
3021
- * Decision table:
3022
- * - no `onThreshold` handler → throw `BudgetExceededError`
3023
- * - `mode === 'sync'` → throw `BudgetExceededError`
3024
- * - `mode === 'auto'` + no listener → throw `BudgetExceededError`
3025
- * - `mode === 'auto'` + listener → throw `BudgetExceededError` (timeout is not extendable)
3027
+ * Decision table (same as `checkLimits`):
3028
+ * - no `onThreshold` handler → throw `BudgetExceededError` (hard stop)
3029
+ * - `mode === 'sync'` → throw `BudgetExceededError` (hard stop)
3030
+ * - `mode === 'auto'` + no listener → throw `BudgetExceededError` (no one to ask)
3031
+ * - `mode === 'auto'` + listener → throw `BudgetThresholdSignal` (negotiated;
3032
+ * a heartbeat-aware policy may extend the timeout)
3026
3033
  */
3027
3034
  checkTimeout() {
3028
3035
  if (this.startTime === null) return;
@@ -5710,7 +5717,10 @@ var NICKNAME_POOL = {
5710
5717
  "lavoisier": { name: "Lavoisier", domain: "chemistry" },
5711
5718
  "mendeleev": { name: "Mendeleev", domain: "chemistry" }
5712
5719
  };
5713
- var ALL_NICKNAMES = Object.values(NICKNAME_POOL);
5720
+ var ALL_NICKNAMES = Object.entries(NICKNAME_POOL);
5721
+ Object.fromEntries(
5722
+ ALL_NICKNAMES.map(([key, entry]) => [entry.name, key])
5723
+ );
5714
5724
  var DOMAIN_PREFERENCES = {
5715
5725
  "security": ["shannon", "turing", "lamarr", "stallman"],
5716
5726
  "bug-hunter": ["darwin", "curie", "feynman", "fermi"],
@@ -5743,17 +5753,16 @@ function assignNickname(role, used) {
5743
5753
  for (const key of preferences) {
5744
5754
  const entry = NICKNAME_POOL[key];
5745
5755
  if (entry && !used.has(key)) {
5746
- return `${entry.name} (${formatRole(role)})`;
5756
+ return { key, display: `${entry.name} (${formatRole(role)})` };
5747
5757
  }
5748
5758
  }
5749
- for (const entry of ALL_NICKNAMES) {
5750
- const key = Object.entries(NICKNAME_POOL).find(([, v]) => v.name === entry.name)?.[0];
5751
- if (key && !used.has(key)) {
5752
- return `${entry.name} (${formatRole(role)})`;
5759
+ for (const [key, entry] of ALL_NICKNAMES) {
5760
+ if (!used.has(key)) {
5761
+ return { key, display: `${entry.name} (${formatRole(role)})` };
5753
5762
  }
5754
5763
  }
5755
5764
  const counter = used.size + 1;
5756
- return `Scientist #${counter} (${formatRole(role)})`;
5765
+ return { key: `scientist-${counter}`, display: `Scientist #${counter} (${formatRole(role)})` };
5757
5766
  }
5758
5767
  function formatRole(role) {
5759
5768
  return role.split(/[-_]/).map((w) => w.charAt(0).toUpperCase() + w.slice(1)).join(" ");
@@ -5840,11 +5849,10 @@ var DefaultMultiAgentCoordinator = class _DefaultMultiAgentCoordinator extends E
5840
5849
  const name = subagent.name?.trim() ?? "";
5841
5850
  const isPlaceholder = name === "" || name.toLowerCase() === role.toLowerCase() || name === "subagent" || name === "adhoc" || name === "generic" || /^slot-/.test(name);
5842
5851
  if (!isPlaceholder) return subagent;
5843
- const nickname = assignNickname(role, this.usedNicknames);
5844
- const baseKey = nickname.split(" ")[0].toLowerCase().replace(/[^a-z0-9-]/g, "-");
5845
- this.usedNicknames.add(baseKey);
5846
- this.subagentNicknames.set(subagentId, baseKey);
5847
- return { ...subagent, name: nickname };
5852
+ const { key, display } = assignNickname(role, this.usedNicknames);
5853
+ this.usedNicknames.add(key);
5854
+ this.subagentNicknames.set(subagentId, key);
5855
+ return { ...subagent, name: display };
5848
5856
  }
5849
5857
  async spawn(subagent) {
5850
5858
  const id = subagent.id || randomUUID();
@@ -6096,23 +6104,32 @@ var DefaultMultiAgentCoordinator = class _DefaultMultiAgentCoordinator extends E
6096
6104
  */
6097
6105
  drainPendingAsAborted(message) {
6098
6106
  const dropped = this.pendingTasks.splice(0, this.pendingTasks.length);
6099
- for (const t of dropped) {
6100
- const synthetic = {
6101
- subagentId: t.subagentId ?? "unassigned",
6102
- taskId: t.id,
6103
- status: "stopped",
6104
- error: {
6105
- kind: "aborted_by_parent",
6106
- message,
6107
- retryable: false
6108
- },
6109
- iterations: 0,
6110
- toolCalls: 0,
6111
- durationMs: 0
6112
- };
6113
- this.completedResults.push(synthetic);
6114
- this.emit("task.completed", { task: t, result: synthetic });
6115
- }
6107
+ for (const t of dropped) this.emitPendingAborted(t, message);
6108
+ }
6109
+ /**
6110
+ * Emit a synthetic `stopped`/`aborted_by_parent` completion for a single
6111
+ * PENDING task — one that was never counted in `inFlight`. This MUST bypass
6112
+ * `recordCompletion`: that path does `inFlight--`, which for a pending task
6113
+ * steals a decrement from a genuinely in-flight task and trips the underflow
6114
+ * guard — suppressing that real task's `task.completed` and hanging its
6115
+ * `awaitTasks()` caller. Pushes the result and fires the event directly.
6116
+ */
6117
+ emitPendingAborted(task, message) {
6118
+ const synthetic = {
6119
+ subagentId: task.subagentId ?? "unassigned",
6120
+ taskId: task.id,
6121
+ status: "stopped",
6122
+ error: {
6123
+ kind: "aborted_by_parent",
6124
+ message,
6125
+ retryable: false
6126
+ },
6127
+ iterations: 0,
6128
+ toolCalls: 0,
6129
+ durationMs: 0
6130
+ };
6131
+ this.completedResults.push(synthetic);
6132
+ this.emit("task.completed", { task, result: synthetic });
6116
6133
  }
6117
6134
  async runDispatched(subagentId, task) {
6118
6135
  const subagent = this.subagents.get(subagentId);
@@ -6373,20 +6390,10 @@ var DefaultMultiAgentCoordinator = class _DefaultMultiAgentCoordinator extends E
6373
6390
  const orphaned = this.pendingTasks.filter((t) => t.subagentId === subagentId);
6374
6391
  this.pendingTasks = this.pendingTasks.filter((t) => t.subagentId !== subagentId);
6375
6392
  for (const t of orphaned) {
6376
- const synthetic = {
6377
- subagentId,
6378
- taskId: t.id,
6379
- status: "stopped",
6380
- error: {
6381
- kind: "aborted_by_parent",
6382
- message: `Subagent "${subagentId}" was removed while task "${t.id}" was pending`,
6383
- retryable: false
6384
- },
6385
- iterations: 0,
6386
- toolCalls: 0,
6387
- durationMs: 0
6388
- };
6389
- this.recordCompletion(synthetic);
6393
+ this.emitPendingAborted(
6394
+ t,
6395
+ `Subagent "${subagentId}" was removed while task "${t.id}" was pending`
6396
+ );
6390
6397
  }
6391
6398
  this.fleetBus?.emit({
6392
6399
  subagentId,
@@ -6764,6 +6771,7 @@ ${personaLine}Task: ${task}
6764
6771
  } catch {
6765
6772
  results = coordinator.results().slice(-taskIds.length);
6766
6773
  }
6774
+ await Promise.allSettled(subagentIds.map((id) => coordinator.remove(id)));
6767
6775
  const allSuccessful = results.length > 0 && results.every((r) => r.status === "success");
6768
6776
  const goalComplete = results.some(
6769
6777
  (r) => r.status === "success" && typeof r.result === "string" && GOAL_COMPLETE_MARKER2.test(r.result)