opencode-swarm 7.183.1 → 7.184.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.
Files changed (123) hide show
  1. package/binaries/win32-arm64/swarm-sandbox-runner.exe +0 -0
  2. package/binaries/win32-x64/swarm-sandbox-runner.exe +0 -0
  3. package/dist/background/delegation-health.d.ts +1 -1
  4. package/dist/background/index.d.ts +1 -0
  5. package/dist/background/pr-event-delivery.d.ts +29 -14
  6. package/dist/background/pr-event-subscribers.d.ts +6 -5
  7. package/dist/background/pr-feedback-event-queue.d.ts +19 -2
  8. package/dist/background/pr-feedback-loop-runtime.d.ts +75 -0
  9. package/dist/background/pr-feedback-loop.d.ts +47 -12
  10. package/dist/cli/{coder-settlement-rserb0hm.js → coder-settlement-yvpewr52.js} +15 -12
  11. package/dist/cli/{config-doctor-r4fmzprn.js → config-doctor-qgwpvrbz.js} +7 -3
  12. package/dist/cli/{core-rzek3e2n.js → core-9qt388hq.js} +4 -4
  13. package/dist/cli/{curation-policy-g0jjwrg5.js → curation-policy-49f8jx48.js} +7 -6
  14. package/dist/cli/{curator-drift-a0r5krfx.js → curator-drift-wf0sm2te.js} +9 -9
  15. package/dist/cli/{curator-v84tfqcr.js → curator-ffz5pxgc.js} +40 -39
  16. package/dist/cli/curator-llm-factory-drs36v1q.js +75 -0
  17. package/dist/cli/{dispatch-p5zjg5e6.js → dispatch-cv89p2y1.js} +1 -1
  18. package/dist/cli/{evidence-summary-service-t4csk176.js → evidence-summary-service-8dfzjnxe.js} +21 -20
  19. package/dist/cli/{gate-evidence-3z04zprn.js → gate-evidence-aa5q30f4.js} +14 -7
  20. package/dist/cli/guardrail-explain-9g5y2gjm.js +76 -0
  21. package/dist/cli/{guardrail-log-cbzdh4qj.js → guardrail-log-0g51p94w.js} +8 -8
  22. package/dist/cli/{guardrail-reset-5e75rz44.js → guardrail-reset-dcbmt2wr.js} +40 -39
  23. package/dist/cli/{hive-promoter-f54nrhqn.js → hive-promoter-2g8nga0y.js} +40 -39
  24. package/dist/cli/{index-31e105jf.js → index-046psajf.js} +80 -2
  25. package/dist/cli/{index-rhw6m7s9.js → index-0874kghs.js} +9 -3
  26. package/dist/cli/{index-6h81yvyc.js → index-131ay7x1.js} +3 -3
  27. package/dist/cli/{index-raws06d3.js → index-2c91cxdv.js} +4 -4
  28. package/dist/cli/{index-9f930sy8.js → index-32vszgv0.js} +3 -3
  29. package/dist/cli/{index-0bpr8vag.js → index-3n5zsp31.js} +2 -2
  30. package/dist/cli/{index-b26hje53.js → index-3skvygca.js} +5 -5
  31. package/dist/cli/{index-w81jmdkt.js → index-456awy1p.js} +2 -2
  32. package/dist/cli/{index-hb1zqz50.js → index-475bkab8.js} +2 -2
  33. package/dist/cli/{index-80qhm8aq.js → index-49ptc9xx.js} +10 -4
  34. package/dist/cli/{index-bsjwchw7.js → index-57swfxyp.js} +8 -8
  35. package/dist/cli/{index-y5hhkx1n.js → index-5ppx86w1.js} +38 -18
  36. package/dist/cli/{index-jb7ywm4w.js → index-6b427dy8.js} +6 -6
  37. package/dist/cli/{index-3qy7v4k1.js → index-6cvdk98y.js} +2 -2
  38. package/dist/cli/{index-hsvsz3mj.js → index-6g664sy8.js} +1 -1
  39. package/dist/cli/{index-8me6m6ew.js → index-76abqm8d.js} +2 -2
  40. package/dist/cli/{index-z425p51d.js → index-7hvy33gc.js} +271 -80
  41. package/dist/cli/{index-4xr4gtwd.js → index-7p4ym4q3.js} +1 -1
  42. package/dist/cli/{index-j8ty457v.js → index-aghd9kcx.js} +2 -2
  43. package/dist/cli/{index-h01p5ygy.js → index-ar2gsn6b.js} +8 -8
  44. package/dist/cli/{index-ak1dd17g.js → index-dbshccrr.js} +3 -3
  45. package/dist/cli/{index-908k7jhw.js → index-depfky1j.js} +158 -27
  46. package/dist/cli/{index-5t08vc6m.js → index-earq3mda.js} +1 -1
  47. package/dist/cli/{index-6dm6ettv.js → index-ejb7ejhd.js} +1 -1
  48. package/dist/cli/{index-3rb5gs4w.js → index-f0nj3d8z.js} +1 -1
  49. package/dist/cli/{index-qjzbs971.js → index-gsgy1psq.js} +4 -4
  50. package/dist/cli/{index-jk05g11c.js → index-jc8pcf0r.js} +7 -7
  51. package/dist/cli/{index-mt0s67hg.js → index-jkxef52n.js} +2 -2
  52. package/dist/cli/{index-wpn7ftw1.js → index-jvk95e6y.js} +2 -2
  53. package/dist/cli/{index-5cve9g2b.js → index-k53a69vb.js} +6 -6
  54. package/dist/cli/{index-1xnse449.js → index-mc72pk74.js} +1 -1
  55. package/dist/cli/{index-w196wb3a.js → index-mz4zz59c.js} +42 -41
  56. package/dist/cli/{index-4hnk9npg.js → index-n107956q.js} +5 -5
  57. package/dist/cli/{index-gaykghrm.js → index-qczxr0wh.js} +12 -10
  58. package/dist/cli/{index-nazzb4em.js → index-s7bseqza.js} +3220 -1893
  59. package/dist/cli/{index-dg3f2sqq.js → index-t7hmqgjy.js} +90 -141
  60. package/dist/cli/{index-08x7gsnf.js → index-w9hxzcz4.js} +2 -2
  61. package/dist/cli/{index-bqphhrwf.js → index-wfdx7yw2.js} +39 -15
  62. package/dist/cli/{index-xtysafzj.js → index-wsb0wbw6.js} +40 -39
  63. package/dist/cli/{index-nmh0s6dg.js → index-wy3zpwjy.js} +1 -1
  64. package/dist/cli/{index-tt705bap.js → index-x1gyqgze.js} +7 -7
  65. package/dist/cli/index-xf69xty9.js +105 -0
  66. package/dist/cli/{index-ydefv5fn.js → index-ya32wfkp.js} +4 -2
  67. package/dist/cli/{index-1hnknn34.js → index-yk0r42nr.js} +4 -4
  68. package/dist/cli/{index-77650pyg.js → index-zzvxj02e.js} +3 -3
  69. package/dist/cli/index.js +41 -40
  70. package/dist/cli/{knowledge-escalator-cs7fjgy0.js → knowledge-escalator-pt21q3eh.js} +14 -13
  71. package/dist/cli/{knowledge-events-262c1jg2.js → knowledge-events-hp96b55k.js} +12 -11
  72. package/dist/cli/{knowledge-link-8kcms7pj.js → knowledge-link-ap2274vm.js} +6 -5
  73. package/dist/cli/{knowledge-store-yjrkfens.js → knowledge-store-rnw1e7zp.js} +7 -6
  74. package/dist/cli/{knowledge-validator-t98cvpt5.js → knowledge-validator-xy7r6eyx.js} +9 -8
  75. package/dist/cli/{mcp-wj6143vj.js → mcp-3nd85kww.js} +15 -1
  76. package/dist/cli/mcp.d.ts +1 -0
  77. package/dist/cli/{model-preflight-tz4ar9ys.js → model-preflight-xe0chjad.js} +40 -39
  78. package/dist/cli/{pending-delegations-vvbkqe24.js → pending-delegations-2pdngdzq.js} +13 -12
  79. package/dist/cli/{pr-subscriptions-maeppcws.js → pr-subscriptions-hxxwszyr.js} +13 -12
  80. package/dist/cli/{pr-workflow-gate-en54gabv.js → pr-workflow-gate-m37ynr6h.js} +40 -39
  81. package/dist/cli/{runner-618229m8.js → runner-yz3ysehf.js} +7 -6
  82. package/dist/cli/{scan-cursor-sxwh1ax8.js → scan-cursor-be9hbq1v.js} +8 -7
  83. package/dist/cli/{schema-fb8vm14k.js → schema-j17hv98z.js} +3 -1
  84. package/dist/cli/{scope-persistence-sc2zhr15.js → scope-persistence-rmt56rma.js} +16 -15
  85. package/dist/cli/{server-7ksq9wr7.js → server-wzrb59mh.js} +40 -39
  86. package/dist/cli/{skill-generator-ccmq47cm.js → skill-generator-vsfya55z.js} +16 -15
  87. package/dist/cli/{snapshot-coordination-init-h8eg88w2.js → snapshot-coordination-init-pc8ykvh8.js} +40 -39
  88. package/dist/cli/{speckit-checkoff-vkqn317p.js → speckit-checkoff-j407j8ew.js} +4 -4
  89. package/dist/cli/{telemetry-vqyy5nha.js → telemetry-39zmx4fp.js} +2 -2
  90. package/dist/cli/{workspace-snapshot-t22m6gbd.js → workspace-snapshot-0q1n1xq5.js} +4 -4
  91. package/dist/cli/{worktree-collision-ownership-8hr7aycc.js → worktree-collision-ownership-je4fb407.js} +14 -13
  92. package/dist/cli/{worktree-isolation-gwq3y9tf.js → worktree-isolation-27rt584e.js} +40 -39
  93. package/dist/commands/doctor.d.ts +5 -0
  94. package/dist/config/schema.d.ts +15 -0
  95. package/dist/context/role-filter.d.ts +2 -0
  96. package/dist/db/qa-gate-session-override.d.ts +12 -12
  97. package/dist/gate-evidence.d.ts +43 -1
  98. package/dist/hooks/final-context-accounting.d.ts +3 -2
  99. package/dist/hooks/guardrails/index.d.ts +13 -7
  100. package/dist/hooks/host-boundary.d.ts +10 -0
  101. package/dist/hooks/system-enhancer.d.ts +9 -2
  102. package/dist/hooks/system-guidance-carrier.d.ts +18 -0
  103. package/dist/index.js +520 -514
  104. package/dist/plan/ledger.d.ts +20 -4
  105. package/dist/plan/manager.d.ts +20 -2
  106. package/dist/services/config-doctor.d.ts +24 -0
  107. package/dist/services/injection-budget.d.ts +56 -8
  108. package/dist/session/hydration-ownership.d.ts +39 -12
  109. package/dist/session/snapshot-coordination-init.d.ts +11 -4
  110. package/dist/session/snapshot-reader.d.ts +9 -4
  111. package/dist/session/snapshot-writer.d.ts +2 -3
  112. package/dist/state.d.ts +35 -5
  113. package/dist/tools/phase-complete.d.ts +1 -0
  114. package/dist/tools/save-plan.d.ts +12 -0
  115. package/dist/tools/update-task-status.d.ts +1 -1
  116. package/dist/utils/project-boundary.d.ts +32 -1
  117. package/dist/workflow/coder-settlement.d.ts +8 -0
  118. package/dist/workflow/task-terminal.d.ts +2 -1
  119. package/dist/workflow/workflow-wal-schema.d.ts +2 -0
  120. package/opencode-swarm.schema.json +8 -0
  121. package/package.json +1 -1
  122. package/dist/cli/curator-llm-factory-xp4hgd8r.js +0 -74
  123. package/dist/cli/guardrail-explain-j2y5sj4d.js +0 -75
@@ -159,8 +159,8 @@ export declare const DelegationLedgerHealthSchema: z.ZodObject<{
159
159
  pressurePct: z.ZodNumber;
160
160
  band: z.ZodEnum<{
161
161
  ok: "ok";
162
- "compact-overdue": "compact-overdue";
163
162
  "fail-closed": "fail-closed";
163
+ "compact-overdue": "compact-overdue";
164
164
  nominal: "nominal";
165
165
  }>;
166
166
  }, z.core.$strict>;
@@ -17,6 +17,7 @@ export { createEvidenceSummaryIntegration, type EvidenceSummaryIntegrationConfig
17
17
  export { type AutomationFrameworkConfig, BackgroundAutomationManager, createAutomationManager, } from './manager';
18
18
  export { PlanSyncWorker, type PlanSyncWorkerOptions, type PlanSyncWorkerStatus, } from './plan-sync-worker';
19
19
  export { type PrEventSubscriberOptions, registerPrEventSubscribers, } from './pr-event-subscribers';
20
+ export { dispatchPrFeedbackOversight, evaluatePrFeedbackCurrentHead, getPrFeedbackLoopRuntime, isPrFeedbackLoopEnabled, type PrFeedbackLoopOversightInput, type PrFeedbackLoopOversightOutcome, type PrFeedbackLoopRuntime, type PrFeedbackLoopRuntimeOptions, type PrFeedbackLoopRuntimeRegistration, registerPrFeedbackLoopRuntime, } from './pr-feedback-loop-runtime';
20
21
  export { PrMonitorWorker, type PrMonitorWorkerOptions, type PrMonitorWorkerStatus, } from './pr-monitor-worker';
21
22
  export { AutomationQueue, type QueueItem, type QueuePriority, type RetryMetadata, } from './queue';
22
23
  export { AutomationStatusArtifact, type AutomationStatusSnapshot, } from './status-artifact';
@@ -7,9 +7,9 @@
7
7
  * prompt, instead of (or before) the passive advisory channel that only
8
8
  * surfaces on the session's next model turn.
9
9
  *
10
- * Registration: `src/index.ts` registers a module-level singleton with the
11
- * plugin SDK client when pr_monitor is enabled with prompt delivery, and
12
- * forwards `session.idle` events to `noteSessionIdle()`.
10
+ * Registration: `src/index.ts` registers one owner per canonical project root
11
+ * with the plugin SDK client when pr_monitor is enabled with prompt delivery,
12
+ * and forwards `session.idle` events to `noteSessionIdle()` with that root.
13
13
  *
14
14
  * Invariant 8 (session state — keyed and bounded): all per-session state is
15
15
  * keyed by sessionID in a bounded map (FIFO eviction beyond
@@ -24,8 +24,10 @@ import type { OpencodeClient } from '@opencode-ai/sdk';
24
24
  import type { PrMonitorConfig } from '../config/schema';
25
25
  import { activatePrWorkflow, readPrWorkflowGateState } from '../hooks/pr-workflow-gate';
26
26
  import { log } from '../utils';
27
+ import { canonicalRootKeyFresh, canonicalRootKeyFreshAsync } from '../utils/canonical-root.js';
27
28
  import { withTimeout } from '../utils/timeout';
28
29
  import { claimPrFeedbackMonitorEvents, readPrFeedbackMonitorQueue } from './pr-feedback-event-queue.js';
30
+ import { notifyPrFeedbackLoop } from './pr-feedback-loop.js';
29
31
  /** A single formatted PR event handed over by pr-event-subscribers. */
30
32
  export interface FormattedPrEvent {
31
33
  /** Automation event type, e.g. 'pr.ci.failed'. */
@@ -38,6 +40,8 @@ export interface FormattedPrEvent {
38
40
  message: string;
39
41
  /** `[pr-monitor:<type>:<repo>#<n>]` — used for queue dedup. */
40
42
  dedupToken: string;
43
+ /** Trusted mode marker produced by the subscriber for prompt delivery. */
44
+ modeSignal?: string;
41
45
  /** Lifecycle intake is durable but cannot enter the current workflow yet. */
42
46
  disposition?: 'queued-for-later';
43
47
  }
@@ -46,6 +50,9 @@ export interface PrEventDeliveryOptions {
46
50
  directory: string;
47
51
  config: PrMonitorConfig;
48
52
  }
53
+ export type PrEventDeliveryRegistration = (() => void) & {
54
+ promote: () => Promise<void>;
55
+ };
49
56
  /** Max sessions tracked at once; oldest-inserted evicted beyond this. */
50
57
  export declare const MAX_TRACKED_SESSIONS = 64;
51
58
  /** Max queued events per session; oldest dropped beyond this. */
@@ -53,15 +60,20 @@ export declare const MAX_QUEUED_EVENTS_PER_SESSION = 20;
53
60
  /** Deadline for the wake prompt call to be accepted by the SDK. */
54
61
  export declare const WAKE_PROMPT_TIMEOUT_MS = 15000;
55
62
  /**
56
- * Register the delivery singleton. Called from plugin init when
57
- * pr_monitor.enabled && event_delivery === 'prompt'. Idempotent the last
58
- * registration wins.
63
+ * Register a delivery owner. Called from plugin init when
64
+ * pr_monitor.enabled && event_delivery === 'prompt'. A same-root re-init
65
+ * replaces only that root; different roots coexist. The returned cleanup is
66
+ * owner-guarded so stale disposal cannot remove a replacement.
67
+ */
68
+ export declare function registerPrEventDelivery(options: PrEventDeliveryOptions): PrEventDeliveryRegistration;
69
+ /**
70
+ * Unregister one owner. The no-argument form is retained for tests and
71
+ * process teardown; an owner token prevents a stale cleanup from removing a
72
+ * newer registration for the same canonical root.
59
73
  */
60
- export declare function registerPrEventDelivery(options: PrEventDeliveryOptions): void;
61
- /** Unregister and drop all per-session state (also used by tests). */
62
- export declare function unregisterPrEventDelivery(): void;
74
+ export declare function unregisterPrEventDelivery(directory?: string, expectedOwnerToken?: string): void;
63
75
  /** Whether a wake deliverer is currently registered. */
64
- export declare function isPrEventDeliveryRegistered(): boolean;
76
+ export declare function isPrEventDeliveryRegistered(directory?: string): boolean;
65
77
  /**
66
78
  * Deliver PR activity to a session. Returns true when the events were
67
79
  * accepted on the wake channel (prompted immediately, queued for the next
@@ -74,13 +86,13 @@ export declare function isPrEventDeliveryRegistered(): boolean;
74
86
  *
75
87
  * Never throws.
76
88
  */
77
- export declare function deliverPrActivity(sessionID: string, events: FormattedPrEvent[]): Promise<boolean>;
89
+ export declare function deliverPrActivity(sessionID: string, events: FormattedPrEvent[], directory?: string): Promise<boolean>;
78
90
  /**
79
91
  * Called from the plugin `event` hook on `session.idle`. Marks the session
80
92
  * idle and flushes any queued events, coalescing them into ONE wake message.
81
93
  * No-op unless delivery is registered. Never throws.
82
94
  */
83
- export declare function noteSessionIdle(sessionID: string): void;
95
+ export declare function noteSessionIdle(sessionID: string, directory?: string): Promise<void>;
84
96
  /**
85
97
  * Build the single-text-part wake message. Events are grouped per PR into
86
98
  * one `<pr-activity>` block each, followed by the standing instruction.
@@ -93,7 +105,7 @@ export declare function buildWakeMessage(events: FormattedPrEvent[]): string;
93
105
  * clients that lack it. Bounded by withTimeout; returns false on any
94
106
  * failure or timeout. Never throws.
95
107
  */
96
- declare function sendWakePrompt(sessionID: string, events: FormattedPrEvent[], messageID: string): Promise<boolean>;
108
+ declare function sendWakePrompt(sessionID: string, events: FormattedPrEvent[], messageID: string, directory?: string): Promise<boolean>;
97
109
  export declare const _internals: {
98
110
  sendWakePrompt: typeof sendWakePrompt;
99
111
  withTimeout: typeof withTimeout;
@@ -101,13 +113,16 @@ export declare const _internals: {
101
113
  activatePrWorkflow: typeof activatePrWorkflow;
102
114
  readPrFeedbackMonitorQueue: typeof readPrFeedbackMonitorQueue;
103
115
  claimPrFeedbackMonitorEvents: typeof claimPrFeedbackMonitorEvents;
116
+ notifyPrFeedbackLoop: typeof notifyPrFeedbackLoop;
117
+ canonicalRootKeyFresh: typeof canonicalRootKeyFresh;
118
+ canonicalRootKeyFreshAsync: typeof canonicalRootKeyFreshAsync;
104
119
  wakePromptTimeoutMs: number;
105
120
  log: typeof log;
106
121
  };
107
122
  /** Test-only visibility into the bounded session map. */
108
123
  export declare function _getTrackedSessionCount(): number;
109
124
  /** Test-only visibility into a session's queue length / drop counter. */
110
- export declare function _getSessionQueueStats(sessionID: string): {
125
+ export declare function _getSessionQueueStats(sessionID: string, directory?: string): {
111
126
  queued: number;
112
127
  dropped: number;
113
128
  busy: boolean;
@@ -24,13 +24,12 @@
24
24
  * are deduped by token inside the delivery queue.
25
25
  */
26
26
  import type { PrMonitorConfig } from '../config/schema';
27
- import { activatePrWorkflow, readPrWorkflowGateState } from '../hooks/pr-workflow-gate';
27
+ import { readPrWorkflowGateState } from '../hooks/pr-workflow-gate';
28
28
  import { getAgentSession } from '../state';
29
29
  import { log } from '../utils';
30
30
  import { getGlobalEventBus } from './event-bus';
31
31
  import { deliverPrActivity, isPrEventDeliveryRegistered } from './pr-event-delivery';
32
- import { enqueuePrFeedbackMonitorEvent } from './pr-feedback-event-queue.js';
33
- import { notifyPrFeedbackLoop } from './pr-feedback-loop.js';
32
+ import { enqueuePrFeedbackMonitorEventIfNotCancelled, notifyPrFeedbackLoop, readPrFeedbackLoopCancellation } from './pr-feedback-loop.js';
34
33
  import { listActive, updateSnapshot } from './pr-subscriptions';
35
34
  export interface PrEventSubscriberOptions {
36
35
  directory: string;
@@ -47,8 +46,8 @@ export declare const _internals: {
47
46
  updateSnapshot: typeof updateSnapshot;
48
47
  getAgentSession: typeof getAgentSession;
49
48
  readPrWorkflowGateState: typeof readPrWorkflowGateState;
50
- activatePrWorkflow: typeof activatePrWorkflow;
51
- enqueuePrFeedbackMonitorEvent: typeof enqueuePrFeedbackMonitorEvent;
49
+ readPrFeedbackLoopCancellation: typeof readPrFeedbackLoopCancellation;
50
+ enqueuePrFeedbackMonitorEvent: typeof enqueuePrFeedbackMonitorEventIfNotCancelled;
52
51
  notifyPrFeedbackLoop: typeof notifyPrFeedbackLoop;
53
52
  deliverPrActivity: typeof deliverPrActivity;
54
53
  isPrEventDeliveryRegistered: typeof isPrEventDeliveryRegistered;
@@ -77,6 +76,8 @@ interface PrEventPayload {
77
76
  reviewDecision?: string;
78
77
  /** pr.merge.conflict_resolved */
79
78
  mergeableState?: string;
79
+ /** Authenticated head observed by the monitor when it emitted the event. */
80
+ headRefOid?: string;
80
81
  }
81
82
  /**
82
83
  * Register subscribers on the global event bus for all gated PR event
@@ -9,7 +9,11 @@ export interface PrFeedbackMonitorEvent {
9
9
  dedupToken: string;
10
10
  authorized: boolean;
11
11
  queuedAt: string;
12
+ /** Head authenticated by the monitor when this event was emitted. */
13
+ headRefOid?: string;
12
14
  claimedWorkflowInstanceId?: string;
15
+ /** Exact process owner paired with the workflow instance id. */
16
+ claimedOwnerPid?: number;
13
17
  claimedAt?: string;
14
18
  }
15
19
  export interface PrFeedbackMonitorQueueRecord {
@@ -18,9 +22,9 @@ export interface PrFeedbackMonitorQueueRecord {
18
22
  sessionID: string;
19
23
  events: PrFeedbackMonitorEvent[];
20
24
  }
21
- export declare function enqueuePrFeedbackMonitorEvent(directory: string, sessionID: string, event: Omit<PrFeedbackMonitorEvent, 'claimedWorkflowInstanceId' | 'claimedAt'>): Promise<PrFeedbackMonitorQueueRecord>;
25
+ export declare function enqueuePrFeedbackMonitorEvent(directory: string, sessionID: string, event: Omit<PrFeedbackMonitorEvent, 'claimedWorkflowInstanceId' | 'claimedAt' | 'claimedOwnerPid'>): Promise<PrFeedbackMonitorQueueRecord>;
22
26
  export declare function readPrFeedbackMonitorQueue(directory: string, sessionID: string): Promise<PrFeedbackMonitorQueueRecord | null>;
23
- export declare function claimPrFeedbackMonitorEvents(directory: string, sessionID: string, workflowInstanceId: string, prUrl: string, dedupTokens?: readonly string[]): Promise<PrFeedbackMonitorEvent[]>;
27
+ export declare function claimPrFeedbackMonitorEvents(directory: string, sessionID: string, workflowInstanceId: string, prUrl: string, dedupTokens?: readonly string[], ownerPid?: number): Promise<PrFeedbackMonitorEvent[]>;
24
28
  /**
25
29
  * Remove queued events by dedup token (#2502 loop cancellation). Claimed but
26
30
  * unsettled events otherwise stay in the queue forever — a claim alone never
@@ -28,17 +32,30 @@ export declare function claimPrFeedbackMonitorEvents(directory: string, sessionI
28
32
  * every other write; returns the tokens actually removed.
29
33
  */
30
34
  export declare function clearPrFeedbackMonitorEvents(directory: string, sessionID: string, dedupTokens: readonly string[]): Promise<string[]>;
35
+ /**
36
+ * Release one exact workflow-instance claim so a retryable pre-settlement
37
+ * admission failure does not strand the event. The token, workflow id, and
38
+ * owner PID are all required: a later worker must never be able to release
39
+ * another worker's claim (or an unrelated event with the same PR URL).
40
+ */
41
+ export declare function releasePrFeedbackMonitorEventClaim(directory: string, sessionID: string, dedupToken: string, workflowInstanceId: string, ownerPid?: number): Promise<boolean>;
31
42
  export declare const _internals: {
32
43
  queueRelativePath: typeof queueRelativePath;
44
+ queueMetadataRelativePath: typeof queueMetadataRelativePath;
33
45
  queueLockRelativePath: typeof queueLockRelativePath;
34
46
  resetQueueCache: () => void;
35
47
  rename: typeof fsp.rename;
36
48
  nowMs: () => number;
37
49
  isProcessAlive: typeof isProcessAlive;
50
+ reclaimAbandonedQueueLock: typeof reclaimAbandonedQueueLock;
51
+ removeQueueLockIfOwned: typeof removeQueueLockIfOwned;
38
52
  beforeQueueFileOpen: (() => Promise<void>) | undefined;
39
53
  beforeQueueLockWrite: (() => Promise<void>) | undefined;
40
54
  };
55
+ declare function reclaimAbandonedQueueLock(lockPath: string): Promise<boolean>;
56
+ declare function removeQueueLockIfOwned(lockPath: string, ownerToken: string): Promise<boolean>;
41
57
  declare function isProcessAlive(pid: number): boolean;
42
58
  declare function queueRelativePath(sessionID: string): string;
59
+ declare function queueMetadataRelativePath(sessionID: string): string;
43
60
  declare function queueLockRelativePath(sessionID: string): string;
44
61
  export {};
@@ -0,0 +1,75 @@
1
+ /**
2
+ * Production composition boundary for the opt-in PR feedback settling loop.
3
+ *
4
+ * The loop itself is deliberately independent of the OpenCode client and of
5
+ * plugin-instance state. This module binds those dependencies to a canonical
6
+ * project root at plugin init and exposes only bounded, fail-closed adapters.
7
+ * Registration is synchronous and side-effect free: no filesystem, Git,
8
+ * network, agent discovery, or model work happens on the init path.
9
+ */
10
+ import type { OpencodeClient } from '@opencode-ai/sdk';
11
+ import type { PluginConfig } from '../config/schema.js';
12
+ import { dispatchEphemeralAgent } from '../evaluation/ephemeral-agent-dispatcher.js';
13
+ import { parseCriticResponseFields } from '../full-auto/critic-response-parser.js';
14
+ import { getPRPollSnapshot } from '../git/pr.js';
15
+ import { canonicalRootKeyFresh, canonicalRootKeyFreshAsync } from '../utils/canonical-root.js';
16
+ import { log } from '../utils/logger.js';
17
+ /** The input shape shared with `pr-feedback-loop` without a runtime import. */
18
+ export interface PrFeedbackLoopOversightInput {
19
+ directory: string;
20
+ sessionID: string;
21
+ eventType: string;
22
+ actionClass: string;
23
+ repoFullName: string;
24
+ prNumber: number;
25
+ head: string | null;
26
+ }
27
+ export interface PrFeedbackLoopOversightOutcome {
28
+ dispatched: boolean;
29
+ verdict?: string;
30
+ decision?: string;
31
+ }
32
+ export type ResolveSessionAgent = (sessionID: string) => string | undefined;
33
+ export interface PrFeedbackLoopRuntimeOptions {
34
+ client: OpencodeClient;
35
+ directory: string;
36
+ config: PluginConfig;
37
+ /** Exact names emitted by this plugin instance's agent factory. */
38
+ agentNames: readonly string[];
39
+ /** Resolves the current agent name from this plugin instance's session state. */
40
+ resolveSessionAgent: ResolveSessionAgent;
41
+ }
42
+ /**
43
+ * Return whether the autonomous PR feedback loop has all of its opt-in gates.
44
+ *
45
+ * Keep this policy in the runtime composition boundary so plugin init and the
46
+ * settling loop cannot drift into subtly different activation semantics.
47
+ */
48
+ export declare function isPrFeedbackLoopEnabled(config: Pick<PluginConfig, 'pr_monitor' | 'pr_feedback_loop'>): boolean;
49
+ export interface PrFeedbackLoopRuntime {
50
+ readonly directory: string;
51
+ evaluateCurrentHead(directory: string, repoFullName: string, prNumber: number): Promise<string | null>;
52
+ dispatchOversight(input: PrFeedbackLoopOversightInput): Promise<PrFeedbackLoopOversightOutcome>;
53
+ }
54
+ export type PrFeedbackLoopRuntimeRegistration = (() => void) & {
55
+ promote: () => Promise<void>;
56
+ };
57
+ /**
58
+ * Register a root-owned runtime and return an exact owner-guarded cleanup.
59
+ * Registration is intentionally synchronous and has no external side effects.
60
+ */
61
+ export declare function registerPrFeedbackLoopRuntime(options: PrFeedbackLoopRuntimeOptions): PrFeedbackLoopRuntimeRegistration;
62
+ /** Look up the runtime for the exact canonical root, or fail closed. */
63
+ export declare function getPrFeedbackLoopRuntime(directory: string): PrFeedbackLoopRuntime | null;
64
+ /** Adapter entry points for the settling loop's production seam. */
65
+ export declare function evaluatePrFeedbackCurrentHead(directory: string, repoFullName: string, prNumber: number): Promise<string | null>;
66
+ export declare function dispatchPrFeedbackOversight(input: PrFeedbackLoopOversightInput): Promise<PrFeedbackLoopOversightOutcome>;
67
+ /** Test-only DI visibility; production behavior still uses these same calls. */
68
+ export declare const _internals: {
69
+ getPRPollSnapshot: typeof getPRPollSnapshot;
70
+ dispatchEphemeralAgent: typeof dispatchEphemeralAgent;
71
+ parseCriticResponseFields: typeof parseCriticResponseFields;
72
+ canonicalRootKeyFresh: typeof canonicalRootKeyFresh;
73
+ canonicalRootKeyFreshAsync: typeof canonicalRootKeyFreshAsync;
74
+ log: typeof log;
75
+ };
@@ -1,5 +1,8 @@
1
1
  import { type PrFeedbackMonitorEvent } from './pr-feedback-event-queue';
2
+ import { listActive } from './pr-subscriptions';
2
3
  export declare const PR_FEEDBACK_LOOP_STATE_REL: string;
4
+ export declare const MAX_IN_FLIGHT_SESSIONS = 64;
5
+ export declare const MAX_CANCELLATION_REQUESTS = 64;
3
6
  export interface PrFeedbackLoopClassification {
4
7
  type: string;
5
8
  actionClass: string;
@@ -51,20 +54,40 @@ export interface PrFeedbackLoopResult {
51
54
  action: PrFeedbackLoopAction | null;
52
55
  terminal: PrFeedbackLoopTerminal | null;
53
56
  }
57
+ /**
58
+ * Durable cancellation state exposed to the PR-event intake boundary.
59
+ *
60
+ * A read failure is deliberately distinct from "not cancelled": callers that
61
+ * can create new queue work must fail closed when the stop barrier cannot be
62
+ * read reliably.
63
+ */
64
+ export interface PrFeedbackLoopCancellationStatus {
65
+ cancelled: boolean;
66
+ unavailable: boolean;
67
+ reason?: string;
68
+ }
54
69
  interface CircuitState {
55
70
  failures: number;
56
71
  openUntil: number;
57
72
  halfOpenProbes: number;
73
+ halfOpenProbeStartedAt?: number;
74
+ halfOpenProbeOwnerToken?: string;
75
+ halfOpenProbeOwnerPid?: number;
58
76
  }
59
77
  interface InFlightClaim {
60
78
  dedupToken: string;
79
+ workflowInstanceId: string;
80
+ ownerPid: number;
61
81
  actionClass: string;
62
82
  head: string | null;
63
83
  performed: boolean;
64
84
  attempts: number;
65
85
  claimedAt: string;
86
+ actionStartedAt?: number;
66
87
  }
67
88
  interface CorrelationState {
89
+ /** Monotonic per-correlation CAS fence; legacy records normalize to zero. */
90
+ revision: number;
68
91
  sessionID: string;
69
92
  repoFullName: string;
70
93
  prNumber: number;
@@ -84,7 +107,7 @@ interface LoopStateV1 {
84
107
  * when the session has no prior settlement correlation). */
85
108
  sessionTerminals: Record<string, PrFeedbackLoopTerminal>;
86
109
  }
87
- export type EvaluateCurrentHead = (repoFullName: string, prNumber: number) => Promise<string | null>;
110
+ export type EvaluateCurrentHead = (directory: string, repoFullName: string, prNumber: number) => Promise<string | null>;
88
111
  export type DispatchOversightInput = {
89
112
  directory: string;
90
113
  sessionID: string;
@@ -122,7 +145,29 @@ export declare const _internals: {
122
145
  corrupt: true;
123
146
  }>;
124
147
  writeState: (directory: string, state: LoopStateV1) => Promise<void>;
148
+ listActive: typeof listActive;
149
+ isProcessAlive: (pid: number) => boolean;
150
+ beforeLoopStateLockWrite?: () => Promise<void>;
151
+ resetLoopStateLock: () => void;
152
+ loopStateLockRelativePath: () => string;
153
+ reclaimAbandonedLoopStateLock: (lockPath: string) => Promise<boolean>;
154
+ removeLoopStateLockIfOwned: (lockPath: string, ownerToken: string) => Promise<boolean>;
125
155
  };
156
+ /** Restore the production dependency bindings after a DI-seam test. */
157
+ export declare function resetLoopInternalsForTests(): void;
158
+ /**
159
+ * Read the current cancellation barrier before admitting new monitor work.
160
+ * This includes an in-process cancellation request while it is being durably
161
+ * recorded, and the session terminal persisted by a completed cancellation.
162
+ */
163
+ export declare function readPrFeedbackLoopCancellation(directory: string, sessionID: string): Promise<PrFeedbackLoopCancellationStatus>;
164
+ /**
165
+ * Admit a new monitor event while holding the loop-state lock. Cancellation
166
+ * persists its stop barrier under this same lock before it clears the queue;
167
+ * keeping the check and enqueue in the loop → queue order prevents a stop
168
+ * from racing between the check and a queue write after cleanup.
169
+ */
170
+ export declare function enqueuePrFeedbackMonitorEventIfNotCancelled(directory: string, sessionID: string, event: Omit<PrFeedbackMonitorEvent, 'claimedWorkflowInstanceId' | 'claimedAt' | 'claimedOwnerPid'>): Promise<boolean>;
126
171
  /**
127
172
  * Process ONE queued monitor event end-to-end for the session (the #2502
128
173
  * completion-fixture unit): claim → classify → authorize → oversight → act →
@@ -147,16 +192,6 @@ export declare function cancelPrFeedbackLoop(directory: string, sessionID: strin
147
192
  clearedEvents: string[];
148
193
  };
149
194
  }>;
150
- /**
151
- * Bounded post-cycle tick (#2502 M7). Settlement today is driven entirely by
152
- * the per-session notify hook (handlePrEvent → notifyPrFeedbackLoop, which is
153
- * itself withTimeout-bounded per settlement); the queue store exposes no
154
- * session enumeration yet, so a cross-session sweep has nothing to iterate.
155
- * When enumeration lands, this becomes the bounded sweep (at most
156
- * TICK_SETTLEMENT_CAP settlements per poll cycle IN TOTAL); until then it is
157
- * an honest no-op that reports zero settlements.
158
- */
159
- export declare function tickPrFeedbackLoop(_directory: string): Promise<number>;
160
195
  /** Notify hook for pr-event-subscribers: fire-and-forget, fail-open. */
161
- export declare function notifyPrFeedbackLoop(directory: string, sessionID: string): void;
196
+ export declare function notifyPrFeedbackLoop(directory: string, sessionID: string): Promise<void>;
162
197
  export {};
@@ -6,6 +6,7 @@ import {
6
6
  assertNoUnsettledCoderDispatch,
7
7
  beginCoderSettlement,
8
8
  completeCoderSettlementCleanup,
9
+ hasUnattributedEmptyScopeMutation,
9
10
  listCoderSettlementWalStates,
10
11
  recordCoderMergeProvenance,
11
12
  recoverCoderSettlement,
@@ -13,22 +14,23 @@ import {
13
14
  releaseCoderDispatchOwnership,
14
15
  settleCoderDispatch,
15
16
  transferCoderSettlementToBackground
16
- } from "./index-y5hhkx1n.js";
17
- import"./index-6h81yvyc.js";
18
- import"./index-0bpr8vag.js";
19
- import"./index-908k7jhw.js";
20
- import"./index-raws06d3.js";
21
- import"./index-nmh0s6dg.js";
17
+ } from "./index-5ppx86w1.js";
18
+ import"./index-131ay7x1.js";
19
+ import"./index-3n5zsp31.js";
20
+ import"./index-depfky1j.js";
21
+ import"./index-2c91cxdv.js";
22
+ import"./index-wy3zpwjy.js";
22
23
  import"./index-2s7dvzff.js";
23
- import"./index-wpn7ftw1.js";
24
- import"./index-77650pyg.js";
25
- import"./index-dg3f2sqq.js";
26
- import"./index-tt705bap.js";
27
- import"./index-1xnse449.js";
24
+ import"./index-jvk95e6y.js";
25
+ import"./index-zzvxj02e.js";
26
+ import"./index-xf69xty9.js";
27
+ import"./index-t7hmqgjy.js";
28
+ import"./index-x1gyqgze.js";
29
+ import"./index-mc72pk74.js";
28
30
  import"./index-c1ggtmpm.js";
29
31
  import"./index-ejhxgyvm.js";
30
32
  import"./index-7g4c7s5r.js";
31
- import"./index-5cve9g2b.js";
33
+ import"./index-k53a69vb.js";
32
34
  import"./index-zxdawwc7.js";
33
35
  import"./index-wzec3c4g.js";
34
36
  import"./index-gknz3bv1.js";
@@ -44,6 +46,7 @@ export {
44
46
  recoverCoderSettlement,
45
47
  recordCoderMergeProvenance,
46
48
  listCoderSettlementWalStates,
49
+ hasUnattributedEmptyScopeMutation,
47
50
  completeCoderSettlementCleanup,
48
51
  beginCoderSettlement,
49
52
  assertNoUnsettledCoderDispatch,
@@ -1,5 +1,7 @@
1
1
  // @bun
2
2
  import {
3
+ CURRENT_CONFIG_FORMAT_VERSION,
4
+ DEFAULT_FLIPS,
3
5
  LEAN_TURBO_GATE_PRODUCERS,
4
6
  applySafeAutoFixes,
5
7
  collectLeanTurboGateSatisfiabilityFindings,
@@ -14,11 +16,11 @@ import {
14
16
  shouldRunOnStartup,
15
17
  writeBackupArtifact,
16
18
  writeDoctorArtifact
17
- } from "./index-31e105jf.js";
19
+ } from "./index-046psajf.js";
18
20
  import"./index-6b295cas.js";
19
21
  import"./index-ry16d01s.js";
20
22
  import"./index-c1ggtmpm.js";
21
- import"./index-rhw6m7s9.js";
23
+ import"./index-0874kghs.js";
22
24
  import"./index-wzec3c4g.js";
23
25
  import"./index-bk5tah7q.js";
24
26
  import"./index-gknz3bv1.js";
@@ -39,5 +41,7 @@ export {
39
41
  createConfigBackup,
40
42
  collectLeanTurboGateSatisfiabilityFindings,
41
43
  applySafeAutoFixes,
42
- LEAN_TURBO_GATE_PRODUCERS
44
+ LEAN_TURBO_GATE_PRODUCERS,
45
+ DEFAULT_FLIPS,
46
+ CURRENT_CONFIG_FORMAT_VERSION
43
47
  };
@@ -14,12 +14,12 @@ import {
14
14
  resolveWorktreeBaseDir,
15
15
  shortenWorktreePath,
16
16
  writeLaneProfileToDiskReal
17
- } from "./index-raws06d3.js";
18
- import"./index-nmh0s6dg.js";
17
+ } from "./index-2c91cxdv.js";
18
+ import"./index-wy3zpwjy.js";
19
19
  import"./index-2s7dvzff.js";
20
- import"./index-1xnse449.js";
20
+ import"./index-mc72pk74.js";
21
21
  import"./index-c1ggtmpm.js";
22
- import"./index-5cve9g2b.js";
22
+ import"./index-k53a69vb.js";
23
23
  import"./index-zxdawwc7.js";
24
24
  import"./index-wzec3c4g.js";
25
25
  import"./index-zpsr8rpc.js";
@@ -5,17 +5,18 @@ import {
5
5
  authorizeCuration,
6
6
  buildConfigFingerprintInput,
7
7
  readCohortConfigFingerprint
8
- } from "./index-5t08vc6m.js";
8
+ } from "./index-earq3mda.js";
9
9
  import"./index-rtry5xyf.js";
10
10
  import"./index-vzm6zre7.js";
11
- import"./index-hb1zqz50.js";
12
- import"./index-dg3f2sqq.js";
13
- import"./index-tt705bap.js";
14
- import"./index-1xnse449.js";
11
+ import"./index-475bkab8.js";
12
+ import"./index-xf69xty9.js";
13
+ import"./index-t7hmqgjy.js";
14
+ import"./index-x1gyqgze.js";
15
+ import"./index-mc72pk74.js";
15
16
  import"./index-c1ggtmpm.js";
16
17
  import"./index-ejhxgyvm.js";
17
18
  import"./index-7g4c7s5r.js";
18
- import"./index-5cve9g2b.js";
19
+ import"./index-k53a69vb.js";
19
20
  import"./index-gknz3bv1.js";
20
21
  import"./index-zpsr8rpc.js";
21
22
  import"./index-zgwm4ryv.js";
@@ -5,23 +5,23 @@ import {
5
5
  readPriorDriftReports,
6
6
  runDeterministicDriftCheck,
7
7
  writeDriftReport
8
- } from "./index-1hnknn34.js";
9
- import"./index-4xr4gtwd.js";
10
- import"./index-8me6m6ew.js";
11
- import"./index-nmh0s6dg.js";
8
+ } from "./index-yk0r42nr.js";
9
+ import"./index-7p4ym4q3.js";
10
+ import"./index-76abqm8d.js";
11
+ import"./index-wy3zpwjy.js";
12
12
  import"./index-2s7dvzff.js";
13
13
  import"./index-0725jpp7.js";
14
- import"./index-08x7gsnf.js";
14
+ import"./index-w9hxzcz4.js";
15
15
  import"./index-rdm3px0g.js";
16
16
  import"./index-ry16d01s.js";
17
- import"./index-1xnse449.js";
17
+ import"./index-mc72pk74.js";
18
18
  import"./index-c1ggtmpm.js";
19
19
  import"./index-ejhxgyvm.js";
20
20
  import"./index-7g4c7s5r.js";
21
- import"./index-5cve9g2b.js";
22
- import"./index-80qhm8aq.js";
21
+ import"./index-k53a69vb.js";
22
+ import"./index-49ptc9xx.js";
23
23
  import"./index-zxdawwc7.js";
24
- import"./index-rhw6m7s9.js";
24
+ import"./index-0874kghs.js";
25
25
  import"./index-wzec3c4g.js";
26
26
  import"./index-bk5tah7q.js";
27
27
  import"./index-gknz3bv1.js";