@opengeni/worker-bundle 1.0.0-canary.0 → 1.0.0

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 (244) hide show
  1. package/dist/activities/agent-run-admission.d.ts +3 -1
  2. package/dist/activities/agent-turn/admission.d.ts +24 -3
  3. package/dist/activities/agent-turn/agent-build.d.ts +4 -0
  4. package/dist/activities/agent-turn/claude-usage-observer.d.ts +58 -0
  5. package/dist/activities/agent-turn/code-search.d.ts +60 -0
  6. package/dist/activities/agent-turn/codex-capacity.d.ts +13 -0
  7. package/dist/activities/agent-turn/codex-plan-entitlement.d.ts +105 -0
  8. package/dist/activities/agent-turn/codex.d.ts +3 -2
  9. package/dist/activities/agent-turn/compaction-prep.d.ts +21 -5
  10. package/dist/activities/agent-turn/credential-leases.d.ts +19 -33
  11. package/dist/activities/agent-turn/credential-restriction.d.ts +3 -0
  12. package/dist/activities/agent-turn/errors.d.ts +82 -11
  13. package/dist/activities/agent-turn/failure-settlement.d.ts +6 -3
  14. package/dist/activities/agent-turn/final-reply.d.ts +18 -0
  15. package/dist/activities/agent-turn/finalization-monitor.d.ts +17 -0
  16. package/dist/activities/agent-turn/finalization.d.ts +4 -2
  17. package/dist/activities/agent-turn/github-repository-bindings.d.ts +2 -0
  18. package/dist/activities/agent-turn/governance-model.d.ts +9 -2
  19. package/dist/activities/agent-turn/history-sink.d.ts +2 -0
  20. package/dist/activities/agent-turn/history.d.ts +2 -0
  21. package/dist/activities/agent-turn/input-wait-reply.d.ts +41 -0
  22. package/dist/activities/agent-turn/media-artifacts.d.ts +5 -3
  23. package/dist/activities/agent-turn/model-call-admission.d.ts +15 -0
  24. package/dist/activities/agent-turn/model-usage.d.ts +6 -0
  25. package/dist/activities/agent-turn/model-wire-dispatch.d.ts +15 -0
  26. package/dist/activities/agent-turn/optional-repositories.d.ts +59 -0
  27. package/dist/activities/agent-turn/provider-dispatch-barrier.d.ts +12 -1
  28. package/dist/activities/agent-turn/quiescence.d.ts +7 -7
  29. package/dist/activities/agent-turn/recovery-warning.d.ts +9 -0
  30. package/dist/activities/agent-turn/refresh-credentials.d.ts +6 -0
  31. package/dist/activities/agent-turn/run-credentials.d.ts +8 -3
  32. package/dist/activities/agent-turn/sandbox-establish.d.ts +2 -1
  33. package/dist/activities/agent-turn/sandbox-provision.d.ts +3 -1
  34. package/dist/activities/agent-turn/sandbox-route.d.ts +3 -20
  35. package/dist/activities/agent-turn/sandbox-runtime.d.ts +2 -2
  36. package/dist/activities/agent-turn/session-title.d.ts +34 -2
  37. package/dist/activities/agent-turn/skill-checkout.d.ts +25 -6
  38. package/dist/activities/agent-turn/skill-read.d.ts +70 -2
  39. package/dist/activities/agent-turn/skill-remove.d.ts +14 -0
  40. package/dist/activities/agent-turn/skill-search.d.ts +3 -1
  41. package/dist/activities/agent-turn/skill-tools.d.ts +15 -2
  42. package/dist/activities/agent-turn/skill-transfer.d.ts +18 -6
  43. package/dist/activities/agent-turn/stream-attempt.d.ts +7 -3
  44. package/dist/activities/agent-turn/subscription-lease.d.ts +38 -0
  45. package/dist/activities/agent-turn/tool-environment.d.ts +56 -6
  46. package/dist/activities/agent-turn/tool-policy.d.ts +43 -0
  47. package/dist/activities/agent-turn/turn-context.d.ts +29 -0
  48. package/dist/activities/agent-turn/turn-sandbox-access.d.ts +3 -0
  49. package/dist/activities/agent-turn/xai-capacity.d.ts +2 -1
  50. package/dist/activities/automations.d.ts +3 -1
  51. package/dist/activities/browser-deadline-checkpoint.d.ts +29 -0
  52. package/dist/activities/codemode-dispatcher.d.ts +9 -2
  53. package/dist/activities/codex-capacity.d.ts +18 -2
  54. package/dist/activities/codex-rotation.d.ts +7 -1
  55. package/dist/activities/context-compaction.d.ts +16 -2
  56. package/dist/activities/gmail-files.d.ts +32 -0
  57. package/dist/activities/goals.d.ts +8 -0
  58. package/dist/activities/knowledge-indexing.d.ts +19 -0
  59. package/dist/activities/mcp-account-routes.d.ts +3 -0
  60. package/dist/activities/mcp-credentials.d.ts +12 -13
  61. package/dist/activities/mcp-operation-authority.d.ts +0 -5
  62. package/dist/activities/model-call-fact-reconciler.d.ts +34 -0
  63. package/dist/activities/open-suffix-resume.d.ts +13 -0
  64. package/dist/activities/parent-wake.d.ts +6 -12
  65. package/dist/activities/retained-screenshots.d.ts +7 -2
  66. package/dist/activities/rig-verification.d.ts +2 -3
  67. package/dist/activities/run-credential-renewal.d.ts +1 -0
  68. package/dist/activities/run-credentials.d.ts +15 -3
  69. package/dist/activities/sandbox-images.d.ts +1 -1
  70. package/dist/activities/sandbox-lease.d.ts +47 -9
  71. package/dist/activities/scheduled-tasks.d.ts +4 -35
  72. package/dist/activities/session-state.d.ts +70 -3
  73. package/dist/activities/types.d.ts +55 -6
  74. package/dist/activities/workspace-capture.d.ts +2 -0
  75. package/dist/activities/workspace-credential-provider.d.ts +46 -0
  76. package/dist/{activities-control-HMFGSKC5.js → activities-control-BNPTRTOE.js} +1896 -418
  77. package/dist/activities-control-BNPTRTOE.js.map +1 -0
  78. package/dist/activities-control.d.ts +182 -4
  79. package/dist/{activities-turn-AP67JADS.js → activities-turn-5LGZOSVU.js} +4476 -1327
  80. package/dist/activities-turn-5LGZOSVU.js.map +1 -0
  81. package/dist/activities.d.ts +182 -4
  82. package/dist/artifact-materializer-entry.js +5 -2
  83. package/dist/artifact-materializer-entry.js.map +1 -1
  84. package/dist/artifact-outbox-entry.js +5 -2
  85. package/dist/artifact-outbox-entry.js.map +1 -1
  86. package/dist/browser-deadline-checkpoint-contract.d.ts +2 -0
  87. package/dist/{chunk-A4XQWVZK.js → chunk-3ZTRWDMN.js} +307 -4
  88. package/dist/chunk-3ZTRWDMN.js.map +1 -0
  89. package/dist/{chunk-RAMNYSAW.js → chunk-4ER3YXOT.js} +22 -4
  90. package/dist/chunk-4ER3YXOT.js.map +1 -0
  91. package/dist/{chunk-CYITU5UH.js → chunk-LJX7Z2KP.js} +1445 -343
  92. package/dist/chunk-LJX7Z2KP.js.map +1 -0
  93. package/dist/editable-artifact-materializer-service.d.ts +2 -2
  94. package/dist/editable-artifact-outbox-service.d.ts +2 -2
  95. package/dist/host-export-pump.d.ts +3 -1
  96. package/dist/host-export.d.ts +1 -1
  97. package/dist/host-export.js +1 -1
  98. package/dist/http.d.ts +1 -1
  99. package/dist/index.d.ts +95 -3
  100. package/dist/index.js +137 -43
  101. package/dist/index.js.map +1 -1
  102. package/dist/observability-metrics.d.ts +118 -8
  103. package/dist/retained-process-diagnostics.d.ts +4 -0
  104. package/dist/retained-process-retry.d.ts +7 -0
  105. package/dist/sandbox-resume.d.ts +55 -13
  106. package/dist/sandbox-routing.d.ts +5 -3
  107. package/dist/sandbox-snapshot-diagnostics.d.ts +20 -0
  108. package/dist/session-event-fanout.d.ts +6 -0
  109. package/dist/warm-capture-holder.d.ts +3 -0
  110. package/dist/worker-service-lifecycle.d.ts +12 -0
  111. package/dist/workflow-bundle.js +273 -41
  112. package/dist/workflows/activities.d.ts +1 -1
  113. package/dist/workflows/browser-deadline-checkpoint.d.ts +9 -0
  114. package/dist/workflows/scheduled-tasks.d.ts +4 -0
  115. package/dist/workflows/session.d.ts +36 -0
  116. package/dist/workflows.d.ts +1 -0
  117. package/package.json +21 -19
  118. package/src/activities/agent-run-admission.ts +17 -1
  119. package/src/activities/agent-turn/admission.ts +66 -3
  120. package/src/activities/agent-turn/agent-build.ts +84 -10
  121. package/src/activities/agent-turn/claim.ts +186 -43
  122. package/src/activities/agent-turn/claude-usage-observer.ts +221 -0
  123. package/src/activities/agent-turn/code-search.ts +275 -0
  124. package/src/activities/agent-turn/codex-capacity.ts +172 -8
  125. package/src/activities/agent-turn/codex-plan-entitlement.ts +254 -0
  126. package/src/activities/agent-turn/codex.ts +13 -5
  127. package/src/activities/agent-turn/compaction-prep.ts +170 -102
  128. package/src/activities/agent-turn/credential-leases.ts +122 -216
  129. package/src/activities/agent-turn/credential-restriction.ts +14 -0
  130. package/src/activities/agent-turn/errors.ts +647 -48
  131. package/src/activities/agent-turn/failure-settlement.ts +682 -130
  132. package/src/activities/agent-turn/final-reply.ts +46 -0
  133. package/src/activities/agent-turn/finalization-monitor.ts +120 -0
  134. package/src/activities/agent-turn/finalization.ts +146 -43
  135. package/src/activities/agent-turn/github-repository-bindings.ts +3 -1
  136. package/src/activities/agent-turn/governance-model.ts +69 -28
  137. package/src/activities/agent-turn/history-sink.ts +16 -2
  138. package/src/activities/agent-turn/history.ts +38 -11
  139. package/src/activities/agent-turn/input-wait-reply.ts +103 -0
  140. package/src/activities/agent-turn/knowledge-source-tools.ts +2 -0
  141. package/src/activities/agent-turn/media-artifacts.ts +2 -1
  142. package/src/activities/agent-turn/model-call-admission.ts +94 -0
  143. package/src/activities/agent-turn/model-usage.ts +64 -3
  144. package/src/activities/agent-turn/model-wire-dispatch.ts +27 -0
  145. package/src/activities/agent-turn/optional-repositories.ts +224 -0
  146. package/src/activities/agent-turn/provider-dispatch-barrier.ts +22 -0
  147. package/src/activities/agent-turn/quiescence.ts +10 -7
  148. package/src/activities/agent-turn/recovery-warning.ts +16 -0
  149. package/src/activities/agent-turn/refresh-credentials.ts +44 -0
  150. package/src/activities/agent-turn/run-credentials.ts +116 -55
  151. package/src/activities/agent-turn/run.ts +320 -93
  152. package/src/activities/agent-turn/sandbox-establish.ts +84 -8
  153. package/src/activities/agent-turn/sandbox-provision.ts +3 -1
  154. package/src/activities/agent-turn/sandbox-route.ts +4 -21
  155. package/src/activities/agent-turn/sandbox-runtime.ts +343 -18
  156. package/src/activities/agent-turn/session-title.ts +81 -5
  157. package/src/activities/agent-turn/skill-checkout.ts +111 -24
  158. package/src/activities/agent-turn/skill-install.ts +1 -1
  159. package/src/activities/agent-turn/skill-read.ts +374 -28
  160. package/src/activities/agent-turn/skill-remove.ts +46 -0
  161. package/src/activities/agent-turn/skill-save.ts +1 -1
  162. package/src/activities/agent-turn/skill-search.ts +10 -1
  163. package/src/activities/agent-turn/skill-selection.ts +4 -0
  164. package/src/activities/agent-turn/skill-tools.ts +112 -18
  165. package/src/activities/agent-turn/skill-transfer.ts +68 -23
  166. package/src/activities/agent-turn/stream-attempt.ts +313 -77
  167. package/src/activities/agent-turn/subscription-lease.ts +115 -0
  168. package/src/activities/agent-turn/tool-environment.ts +316 -167
  169. package/src/activities/agent-turn/tool-policy.ts +80 -1
  170. package/src/activities/agent-turn/turn-context.ts +35 -0
  171. package/src/activities/agent-turn/turn-sandbox-access.ts +7 -1
  172. package/src/activities/agent-turn/xai-capacity.ts +94 -51
  173. package/src/activities/automations.ts +76 -4
  174. package/src/activities/browser-deadline-checkpoint.ts +279 -0
  175. package/src/activities/capabilities.ts +108 -11
  176. package/src/activities/codemode-dispatcher.ts +36 -8
  177. package/src/activities/codex-capacity.ts +60 -25
  178. package/src/activities/codex-rotation.ts +39 -17
  179. package/src/activities/context-compaction.ts +75 -18
  180. package/src/activities/gmail-files.ts +88 -0
  181. package/src/activities/goals.ts +116 -121
  182. package/src/activities/google-drive-publication.ts +1 -3
  183. package/src/activities/image-generation-operation.ts +1 -1
  184. package/src/activities/knowledge-indexing.ts +269 -15
  185. package/src/activities/knowledge-source-sync.ts +10 -0
  186. package/src/activities/mcp-account-routes.ts +17 -0
  187. package/src/activities/mcp-credentials.ts +83 -194
  188. package/src/activities/mcp-operation-authority.ts +16 -41
  189. package/src/activities/model-call-fact-reconciler.ts +112 -0
  190. package/src/activities/open-suffix-resume.ts +15 -2
  191. package/src/activities/parent-wake.ts +46 -21
  192. package/src/activities/retained-screenshots.ts +82 -11
  193. package/src/activities/rig-verification.ts +38 -37
  194. package/src/activities/run-credential-renewal.ts +13 -1
  195. package/src/activities/run-credentials.ts +59 -17
  196. package/src/activities/run-input.ts +25 -16
  197. package/src/activities/sandbox-images.ts +0 -1
  198. package/src/activities/sandbox-lease.ts +798 -82
  199. package/src/activities/scheduled-tasks.ts +550 -178
  200. package/src/activities/session-state.ts +245 -6
  201. package/src/activities/site-auth-maintenance.ts +3 -0
  202. package/src/activities/types.ts +72 -5
  203. package/src/activities/workflow-wake.ts +2 -17
  204. package/src/activities/workspace-capture.ts +13 -2
  205. package/src/activities/workspace-credential-provider.ts +283 -0
  206. package/src/activities-control.ts +4 -0
  207. package/src/activities-turn.ts +5 -0
  208. package/src/activities.ts +13 -0
  209. package/src/activity-services.ts +16 -4
  210. package/src/browser-deadline-checkpoint-contract.ts +5 -0
  211. package/src/editable-artifact-hint-broker.ts +3 -0
  212. package/src/editable-artifact-materializer-service.ts +7 -3
  213. package/src/editable-artifact-outbox-service.ts +4 -4
  214. package/src/github-rest-mcp.ts +1 -2
  215. package/src/host-export-pump.ts +26 -4
  216. package/src/host-export.ts +3 -0
  217. package/src/http.ts +4 -2
  218. package/src/index.ts +99 -37
  219. package/src/observability-metrics.ts +510 -5
  220. package/src/personal-github-git-credentials.ts +2 -1
  221. package/src/pr-review-credentials.ts +1 -3
  222. package/src/retained-process-diagnostics.ts +50 -0
  223. package/src/retained-process-retry.ts +36 -0
  224. package/src/sandbox-resume.ts +388 -101
  225. package/src/sandbox-routing.ts +150 -25
  226. package/src/sandbox-snapshot-diagnostics.ts +112 -0
  227. package/src/session-event-fanout.ts +23 -0
  228. package/src/warm-capture-holder.ts +15 -0
  229. package/src/worker-service-lifecycle.ts +53 -0
  230. package/src/workflows/activities.ts +16 -1
  231. package/src/workflows/browser-deadline-checkpoint.ts +50 -0
  232. package/src/workflows/file-upload-reaper.ts +2 -0
  233. package/src/workflows/scheduled-tasks.ts +26 -13
  234. package/src/workflows/session.ts +242 -22
  235. package/src/workflows.ts +4 -0
  236. package/dist/activities/agent-turn/knowledge-sources.d.ts +0 -20
  237. package/dist/activities/packs.d.ts +0 -55
  238. package/dist/activities-control-HMFGSKC5.js.map +0 -1
  239. package/dist/activities-turn-AP67JADS.js.map +0 -1
  240. package/dist/chunk-A4XQWVZK.js.map +0 -1
  241. package/dist/chunk-CYITU5UH.js.map +0 -1
  242. package/dist/chunk-RAMNYSAW.js.map +0 -1
  243. package/src/activities/agent-turn/knowledge-sources.ts +0 -86
  244. package/src/activities/packs.ts +0 -166
@@ -83,6 +83,82 @@ export function structuredToolTransportForTurn(
83
83
  );
84
84
  }
85
85
 
86
+ /**
87
+ * `text.verbosity: "low"` is the Codex CLI default for its GPT-5-family models
88
+ * and keeps final answers short. Send it only where the wire is known to accept
89
+ * it: the ChatGPT/Codex subscription backend, direct OpenAI Responses, and the
90
+ * Azure OpenAI Responses wire, where the parallel session-title request already
91
+ * sends the same field with the turn's model. Gateways, xAI, other
92
+ * OpenAI-compatible endpoints and chat wires keep their provider default. The
93
+ * result depends only on the route and model, so a session sends the same value
94
+ * on every request until its model changes, and a model change already starts a
95
+ * new prompt-cache prefix.
96
+ */
97
+ export function textVerbosityForTurn(
98
+ resolvedModel: {
99
+ provider: {
100
+ id: string;
101
+ kind: ResolvedModelProvider["kind"];
102
+ api: ModelProviderApi;
103
+ wireProfile: "openai" | "azure-openai";
104
+ builtin: boolean;
105
+ baseUrl?: string | undefined;
106
+ };
107
+ } | null,
108
+ upstreamModelId: string,
109
+ ): "low" | undefined {
110
+ if (resolvedModel?.provider.api !== "responses") return undefined;
111
+ const provider = resolvedModel.provider;
112
+ const acceptsVerbosity =
113
+ provider.kind === "codex-subscription" ||
114
+ provider.wireProfile === "azure-openai" ||
115
+ (provider.builtin && provider.id === "openai" && isDirectOpenAiApiBaseUrl(provider.baseUrl));
116
+ return acceptsVerbosity && modelAcceptsTextVerbosity(upstreamModelId) ? "low" : undefined;
117
+ }
118
+
119
+ // GPT-5 and later accept low/medium/high. Earlier models and the -codex and
120
+ // -chat variants accept only the default, so a non-default value is rejected.
121
+ function modelAcceptsTextVerbosity(upstreamModelId: string): boolean {
122
+ return (
123
+ /^gpt-(?:[5-9]|[1-9]\d)(?:[.-]|$)/.test(upstreamModelId) &&
124
+ !/-(?:codex|chat)(?:-|$)/.test(upstreamModelId)
125
+ );
126
+ }
127
+
128
+ /**
129
+ * Ask supported reasoning Responses routes for their provider-selected summary
130
+ * format. This is public summary text, never private or encrypted reasoning.
131
+ * Codex and unverified compatible wires retain the existing detailed setting.
132
+ */
133
+ export function reasoningSummaryForTurn(
134
+ resolvedModel: {
135
+ provider: {
136
+ id: string;
137
+ api: ModelProviderApi;
138
+ wireProfile: "openai" | "azure-openai";
139
+ builtin: boolean;
140
+ baseUrl?: string | undefined;
141
+ };
142
+ configured: {
143
+ upstreamModelId: string;
144
+ capabilities: { reasoning: { runnable: boolean } };
145
+ };
146
+ } | null,
147
+ ): "auto" | undefined {
148
+ if (
149
+ resolvedModel?.provider.api !== "responses" ||
150
+ !resolvedModel.configured.capabilities.reasoning.runnable ||
151
+ !modelAcceptsTextVerbosity(resolvedModel.configured.upstreamModelId)
152
+ ) {
153
+ return undefined;
154
+ }
155
+ const provider = resolvedModel.provider;
156
+ return provider.wireProfile === "azure-openai" ||
157
+ (provider.builtin && provider.id === "openai" && isDirectOpenAiApiBaseUrl(provider.baseUrl))
158
+ ? "auto"
159
+ : undefined;
160
+ }
161
+
86
162
  /**
87
163
  * Progressive tool disclosure is universal for supported OpenGeni turns; only
88
164
  * its contained transport differs. Codex keeps its native path, built-in direct
@@ -218,7 +294,10 @@ export function modelAttachmentInputPolicyForTurn(
218
294
  };
219
295
  } | null,
220
296
  ): ModelAttachmentInputPolicy {
221
- const typedTransport = resolvedModel === null || resolvedModel.provider.api === "responses";
297
+ const typedTransport =
298
+ resolvedModel === null ||
299
+ resolvedModel.provider.api === "responses" ||
300
+ resolvedModel.provider.api === "anthropic-messages";
222
301
  return {
223
302
  supportsImageInput: typedTransport && modelSupportsImageInputForTurn(resolvedModel),
224
303
  inputFileMediaTypes: [],
@@ -1,3 +1,4 @@
1
+ import type { TurnHeartbeatDetails } from "../../op-journal";
1
2
  import type { Settings } from "@opengeni/config";
2
3
  import type { CodexUsageHeaderSnapshot } from "@opengeni/codex";
3
4
  import type { AppendEventInput, ApplySessionTurnSettlementInput } from "@opengeni/db";
@@ -25,6 +26,7 @@ import type { TurnOutcome } from "../../observability-metrics";
25
26
  import type { ResumedTurnSandbox, TurnSandboxLeaseHolderId } from "../../sandbox-resume";
26
27
  import type { TurnEventPublisher } from "./model-usage";
27
28
  import type { TurnSandboxProvisioner } from "./sandbox-provision";
29
+ import { InitialModelWireDispatchClock } from "./model-wire-dispatch";
28
30
 
29
31
  /** Stamps the claimed turn/attempt ids onto a phase's own outcome. */
30
32
  export type ClaimedResult = (
@@ -47,6 +49,7 @@ export type TurnSettleFn = (input: {
47
49
  sessionStatus: SessionStatus;
48
50
  activeTurnId: string | null;
49
51
  suppressGoalContinuation?: boolean;
52
+ allowanceGoalPause?: ApplySessionTurnSettlementInput["allowanceGoalPause"];
50
53
  consumeRequestedCompactionFailure?: boolean;
51
54
  runState?: ApplySessionTurnSettlementInput["runState"];
52
55
  }) => Promise<boolean>;
@@ -65,6 +68,7 @@ export type AttemptIdentityState = {
65
68
  triggerEventId: string | undefined;
66
69
  executionGeneration: number;
67
70
  providerRecoveryCount: number;
71
+ claudeAuthRecovery?: { credentialId: string; credentialVersion: number } | undefined;
68
72
  modelRequestStarted: boolean;
69
73
  redispatchesAtDispatch: number;
70
74
  // Held for same-turn recovery: an approval-decision rerun must re-enter
@@ -75,6 +79,7 @@ export type AttemptIdentityState = {
75
79
  export type BillingState = {
76
80
  isCodexTurn: boolean;
77
81
  isXaiTurn: boolean;
82
+ isClaudeTurn: boolean;
78
83
  isExternallyBilledTurn: boolean;
79
84
  chargesOpenGeniCredits: boolean;
80
85
  countsTowardTokenCap: boolean;
@@ -112,10 +117,14 @@ export type SandboxRuntimeState = {
112
117
  };
113
118
 
114
119
  export type RenewalState = {
120
+ /** Secret-only local state; closed on every attempt finalization path. */
121
+ runMcpCredentials?: { close(): void };
115
122
  gitCredentialRenewals: GitCredentialRenewalController[];
116
123
  gitCredentialRenewalClosed: boolean;
117
124
  runCredentialRenewal: RunCredentialRenewalController | null;
118
125
  runCredentialRenewalClosed: boolean;
126
+ /** Outcome of the most recent renewal attempt, for on-demand refresh reporting. */
127
+ runCredentialRenewalOutcome: "completed" | "auth_needed" | "error" | null;
119
128
  runCredentialSession: RunCredentialCommandSession | null;
120
129
  codemodeTokenRenewal: CodemodeTokenRenewalController | null;
121
130
  codemodeTokenRenewalClosed: boolean;
@@ -123,6 +132,7 @@ export type RenewalState = {
123
132
  };
124
133
 
125
134
  export type EventingState = {
135
+ heartbeatDetails: TurnHeartbeatDetails | null;
126
136
  heartbeatTimer: ReturnType<typeof startActivityHeartbeat> | undefined;
127
137
  batcher: ReturnType<typeof createRuntimeBatcher> | null;
128
138
  preparedTools: Awaited<ReturnType<OpenGeniRuntime["prepareTools"]>> | null;
@@ -138,7 +148,10 @@ export type EventingState = {
138
148
  firstModelRequestPreparationStartedAt: number | null;
139
149
  firstModelRequestPreparationRecorded: boolean;
140
150
  firstModelRequestCheckpointAt: number | null;
151
+ initialModelWireDispatch: InitialModelWireDispatchClock;
141
152
  companyBrainContextContributions: readonly ModelContextContributionSummary[] | null;
153
+ /** Skill ids in this turn's frozen, model-visible Skill index; telemetry only. */
154
+ modelVisibleSkillIds: ReadonlySet<string> | null;
142
155
  };
143
156
 
144
157
  /** Rig telemetry (M3): set once the session loads; empty string for a rig-less
@@ -157,8 +170,18 @@ export type ProviderTurnState = {
157
170
  effectiveCodexCredentialVersion: number | null;
158
171
  /** Frozen alternate-account ceiling observed by the fenced allocator. */
159
172
  codexCredentialFailoverLimit: number;
173
+ /**
174
+ * Accepted product model id (`codex/<slug>`) the Codex allocator filtered
175
+ * for. Failure settlement scopes plan entitlement and failover to it.
176
+ */
177
+ codexProductModelId?: string | null;
160
178
  /** Accepted Codex allocator policy captured with the first durable lease. */
161
179
  codexPolicySnapshot: CodexCredentialPolicySnapshotV1 | null;
180
+ effectiveClaudeCredentialId: string | null;
181
+ effectiveClaudeCredentialVersion: number | null;
182
+ claudeUpstreamModelId: string | null;
183
+ claudeRotationEnabled: boolean;
184
+ claudeAuthoritySnapshot: XaiProviderAccountAuthoritySnapshotV1 | null;
162
185
  effectiveXaiCredentialId: string | null;
163
186
  xaiRotationEnabled: boolean;
164
187
  xaiAuthoritySnapshot: XaiProviderAccountAuthoritySnapshotV1 | null;
@@ -177,6 +200,7 @@ export type ProviderTurnState = {
177
200
  // scraped. Lives on the turn context so the finalizer sees it; the sink is
178
201
  // wired into codexContext.onUsageHeaders by the orchestrator.
179
202
  latestCodexUsage: CodexUsageHeaderSnapshot | null;
203
+ latestClaudeUsage: Map<string, import("./claude-usage-observer").CapturedClaudeUsage>;
180
204
  lastCodexRequestOpaqueArtifacts: readonly string[];
181
205
  };
182
206
 
@@ -216,6 +240,7 @@ export function createTurnContext(input: {
216
240
  billingState: {
217
241
  isCodexTurn: false,
218
242
  isXaiTurn: false,
243
+ isClaudeTurn: false,
219
244
  isExternallyBilledTurn: false,
220
245
  chargesOpenGeniCredits: true,
221
246
  countsTowardTokenCap: true,
@@ -247,6 +272,7 @@ export function createTurnContext(input: {
247
272
  gitCredentialRenewals: [],
248
273
  gitCredentialRenewalClosed: false,
249
274
  runCredentialRenewal: null,
275
+ runCredentialRenewalOutcome: null,
250
276
  runCredentialRenewalClosed: false,
251
277
  runCredentialSession: null,
252
278
  codemodeTokenRenewal: null,
@@ -254,6 +280,7 @@ export function createTurnContext(input: {
254
280
  publishedRunCredentialNotices: new Set(),
255
281
  },
256
282
  eventing: {
283
+ heartbeatDetails: null,
257
284
  heartbeatTimer: undefined,
258
285
  batcher: null,
259
286
  preparedTools: null,
@@ -269,7 +296,9 @@ export function createTurnContext(input: {
269
296
  firstModelRequestPreparationStartedAt: null,
270
297
  firstModelRequestPreparationRecorded: false,
271
298
  firstModelRequestCheckpointAt: null,
299
+ initialModelWireDispatch: new InitialModelWireDispatchClock(),
272
300
  companyBrainContextContributions: null,
301
+ modelVisibleSkillIds: null,
273
302
  },
274
303
  workspaceRefs: {
275
304
  variableSetId: "",
@@ -281,6 +310,11 @@ export function createTurnContext(input: {
281
310
  effectiveCodexCredentialVersion: null,
282
311
  codexCredentialFailoverLimit: 1,
283
312
  codexPolicySnapshot: null,
313
+ effectiveClaudeCredentialId: null,
314
+ effectiveClaudeCredentialVersion: null,
315
+ claudeUpstreamModelId: null,
316
+ claudeRotationEnabled: false,
317
+ claudeAuthoritySnapshot: null,
284
318
  effectiveXaiCredentialId: null,
285
319
  xaiRotationEnabled: false,
286
320
  xaiAuthoritySnapshot: null,
@@ -288,6 +322,7 @@ export function createTurnContext(input: {
288
322
  xaiCredentialQuarantined: false,
289
323
  priorSessionCodexCredentialId: null,
290
324
  latestCodexUsage: null,
325
+ latestClaudeUsage: new Map(),
291
326
  lastCodexRequestOpaqueArtifacts: [],
292
327
  },
293
328
  };
@@ -13,6 +13,12 @@ export type ResolvedTurnSandboxAccess = Readonly<{
13
13
  leaseEpoch: number;
14
14
  }>;
15
15
 
16
+ /** The lazy wrapper remains the agent's owner even after provisioning fills
17
+ * resolvedSandbox with the raw provider handle for capture and release. */
18
+ export function ownedTurnSandboxForAgent(sandboxState: TurnSandboxAccessState) {
19
+ return sandboxState.lazyOwnedSandbox ?? sandboxState.resolvedSandbox?.established;
20
+ }
21
+
16
22
  /** Join the turn's canonical sandbox boundary and return its active routed session. */
17
23
  export async function resolveTurnSandboxAccess(
18
24
  sandboxState: TurnSandboxAccessState,
@@ -24,7 +30,7 @@ export async function resolveTurnSandboxAccess(
24
30
  sandbox = await sandboxState.turnSandboxProvisioner.get();
25
31
  }
26
32
 
27
- const session = (sandboxState.lazyOwnedSandbox?.session ??
33
+ const session = (ownedTurnSandboxForAgent(sandboxState)?.session ??
28
34
  sandbox?.established.session ??
29
35
  sdkOwnedSandboxSession) as ChannelASession | null;
30
36
  if (!session) throw new Error(unavailableMessage);
@@ -7,14 +7,21 @@ import {
7
7
  recordXaiSessionLastAccount,
8
8
  XAI_CREDENTIAL_LEASE_TTL_MS,
9
9
  armXaiCapacityWait,
10
+ acquireClaudeCredentialLease,
11
+ getClaudeSessionAccountPin,
12
+ setClaudeSessionAccountPin,
13
+ recordClaudeSessionLastAccount,
14
+ CLAUDE_CREDENTIAL_LEASE_TTL_MS,
15
+ armClaudeCapacityWait,
10
16
  } from "@opengeni/db";
11
17
  import { publishDurableSessionEvents } from "@opengeni/events";
12
18
 
13
19
  import type { CapacityPhaseDeps, CapacityPhaseOutcome } from "./codex-capacity";
14
20
  import { refreshExhaustedXaiQuota } from "../xai-quota";
15
21
 
16
- export async function selectXaiTurnCapacity(
22
+ async function selectScopedSubscriptionTurnCapacity(
17
23
  deps: CapacityPhaseDeps,
24
+ provider: "xai" | "claude",
18
25
  ): Promise<CapacityPhaseOutcome> {
19
26
  const {
20
27
  input,
@@ -30,32 +37,50 @@ export async function selectXaiTurnCapacity(
30
37
  turn,
31
38
  } = deps;
32
39
 
33
- if (billingState.isXaiTurn) {
34
- const authoritySnapshot = turn.xaiProviderAccountAuthoritySnapshot;
35
- providerTurn.xaiAuthoritySnapshot = authoritySnapshot;
40
+ const claude = provider === "claude";
41
+ const name = claude ? "Claude" : "SuperGrok";
42
+ const acquireLease = claude ? acquireClaudeCredentialLease : acquireXaiCredentialLease;
43
+ const getPin = claude ? getClaudeSessionAccountPin : getXaiSessionAccountPin;
44
+ const setPin = claude ? setClaudeSessionAccountPin : setXaiSessionAccountPin;
45
+ const recordLastAccount = claude ? recordClaudeSessionLastAccount : recordXaiSessionLastAccount;
46
+ const armWait = claude ? armClaudeCapacityWait : armXaiCapacityWait;
47
+ const lease = claude ? leases.claude : leases.xai;
48
+ const credentialKey = claude ? "effectiveClaudeCredentialId" : "effectiveXaiCredentialId";
49
+ const rotationKey = claude ? "claudeRotationEnabled" : "xaiRotationEnabled";
50
+ const authorityKey = claude ? "claudeAuthoritySnapshot" : "xaiAuthoritySnapshot";
51
+ if (claude ? billingState.isClaudeTurn : billingState.isXaiTurn) {
52
+ const authoritySnapshot = claude
53
+ ? turn.claudeProviderAccountAuthoritySnapshot
54
+ : turn.xaiProviderAccountAuthoritySnapshot;
55
+ providerTurn[authorityKey] = authoritySnapshot;
56
+ if (claude) providerTurn.claudeUpstreamModelId = deps.turnExecutionPolicy.upstreamModelId;
36
57
  const subjectId =
37
- authoritySnapshot.scope === "user" ? turn.initiatingHumanSubjectId : "worker:xai-workspace";
58
+ authoritySnapshot.scope === "user"
59
+ ? turn.initiatingHumanSubjectId
60
+ : "worker:" + provider + "-workspace";
38
61
  if (!subjectId) {
39
- throw new Error("User-scoped SuperGrok work has no frozen initiating human");
62
+ throw new Error("User-scoped " + name + " work has no frozen initiating human");
40
63
  }
41
- const sessionPin = await getXaiSessionAccountPin(db, {
64
+ const sessionPin = await getPin(db, {
42
65
  workspaceId: input.workspaceId,
43
66
  subjectId,
44
67
  sessionId: input.sessionId,
45
68
  authoritySnapshot,
46
69
  });
70
+ if (!claude)
71
+ await refreshExhaustedXaiQuota({
72
+ db,
73
+ settings: deps.settings,
74
+ accountId: input.accountId,
75
+ workspaceId: input.workspaceId,
76
+ subjectId,
77
+ sessionId: input.sessionId,
78
+ turnId: turn.id,
79
+ authoritySnapshot,
80
+ });
47
81
  const leaseStartedAtMs = performance.now();
48
- await refreshExhaustedXaiQuota({
49
- db,
50
- settings: deps.settings,
51
- accountId: input.accountId,
52
- workspaceId: input.workspaceId,
53
- subjectId,
54
- sessionId: input.sessionId,
55
- turnId: turn.id,
56
- authoritySnapshot,
57
- });
58
- const leased = await acquireXaiCredentialLease(db, {
82
+ const leased = await acquireLease(db, {
83
+ upstreamModelId: deps.turnExecutionPolicy.upstreamModelId,
59
84
  modelId: deps.turnExecutionPolicy.productModelId,
60
85
  accountId: input.accountId,
61
86
  workspaceId: input.workspaceId,
@@ -70,20 +95,20 @@ export async function selectXaiTurnCapacity(
70
95
  ? sessionPin.pinSource
71
96
  : null,
72
97
  });
73
- providerTurn.effectiveXaiCredentialId = leased.credentialId;
74
- providerTurn.xaiRotationEnabled = leased.rotationEnabled;
75
- leases.xai.subjectId = subjectId;
76
- leases.xai.holderId = leased.holderId;
77
- leases.xai.generation = leased.generation;
78
- leases.xai.confirmedUntilMs = leased.leasedUntil
79
- ? leaseStartedAtMs + XAI_CREDENTIAL_LEASE_TTL_MS
98
+ providerTurn[credentialKey] = leased.credentialId;
99
+ providerTurn[rotationKey] = leased.rotationEnabled;
100
+ lease.subjectId = subjectId;
101
+ lease.holderId = leased.holderId;
102
+ lease.generation = leased.generation;
103
+ lease.confirmedUntilMs = leased.leasedUntil
104
+ ? leaseStartedAtMs + (claude ? CLAUDE_CREDENTIAL_LEASE_TTL_MS : XAI_CREDENTIAL_LEASE_TTL_MS)
80
105
  : null;
81
- leases.xai.held =
82
- providerTurn.effectiveXaiCredentialId !== null &&
106
+ lease.held =
107
+ providerTurn[credentialKey] !== null &&
83
108
  leased.holderId !== null &&
84
109
  leased.generation !== null &&
85
- leases.xai.confirmedUntilMs !== null;
86
- if (!providerTurn.effectiveXaiCredentialId) {
110
+ lease.confirmedUntilMs !== null;
111
+ if (!providerTurn[credentialKey]) {
87
112
  const relevant =
88
113
  sessionPin?.pinnedCredentialId && sessionPin.pinSource !== "policy"
89
114
  ? leased.accounts.filter((account) => account.id === sessionPin.pinnedCredentialId)
@@ -98,13 +123,13 @@ export async function selectXaiTurnCapacity(
98
123
  ),
99
124
  )
100
125
  )
101
- throw new Error("This model is disabled for the selected SuperGrok subscription");
126
+ throw new Error("This model is disabled for the selected " + name + " subscription");
102
127
  const connected = leased.accounts.length;
103
128
  const allocatorEnabled = leased.accounts.filter((account) => account.allocatorEnabled).length;
104
129
  if (connected === 0) {
105
130
  throw Object.assign(
106
- new Error("No SuperGrok subscription account is connected for this authority scope"),
107
- { code: "xai_not_connected" },
131
+ new Error("No " + name + " subscription account is connected for this authority scope"),
132
+ { code: provider + "_not_connected" },
108
133
  );
109
134
  }
110
135
  if (turn.source === "compaction") {
@@ -115,7 +140,7 @@ export async function selectXaiTurnCapacity(
115
140
  type: "turn.cancelled",
116
141
  payload: {
117
142
  maintenance: "context_compaction",
118
- reason: "xai_capacity_unavailable",
143
+ reason: provider + "_capacity_unavailable",
119
144
  requestPreserved: true,
120
145
  },
121
146
  },
@@ -141,14 +166,16 @@ export async function selectXaiTurnCapacity(
141
166
  const futureResets = leased.accounts
142
167
  .map((account) => account.exhaustedUntil)
143
168
  .filter((date): date is Date => date !== null && date > now);
144
- const earliestResetAt = futureResets.length
145
- ? new Date(Math.min(...futureResets.map((date) => date.getTime())))
146
- : null;
169
+ const earliestResetAt = claude
170
+ ? (leased.nextCheckAt ?? null)
171
+ : futureResets.length
172
+ ? new Date(Math.min(...futureResets.map((date) => date.getTime())))
173
+ : null;
147
174
  const error =
148
175
  allocatorEnabled === 0
149
- ? "All connected SuperGrok subscription accounts are disabled for allocation"
150
- : "All connected SuperGrok subscription accounts are temporarily unavailable";
151
- const armed = await armXaiCapacityWait(db, {
176
+ ? "All connected " + name + " subscription accounts are disabled for allocation"
177
+ : "All connected " + name + " subscription accounts are temporarily unavailable";
178
+ const armed = await armWait(db, {
152
179
  accountId: input.accountId,
153
180
  workspaceId: input.workspaceId,
154
181
  subjectId,
@@ -162,7 +189,10 @@ export async function selectXaiTurnCapacity(
162
189
  earliestResetAt,
163
190
  failurePayload: {
164
191
  error,
165
- code: allocatorEnabled === 0 ? "xai_allocator_disabled" : "xai_capacity_unavailable",
192
+ code:
193
+ allocatorEnabled === 0
194
+ ? provider + "_allocator_disabled"
195
+ : provider + "_capacity_unavailable",
166
196
  detail: "waiting for an eligible account, reconnect, pin change, or quota reset",
167
197
  },
168
198
  });
@@ -174,7 +204,7 @@ export async function selectXaiTurnCapacity(
174
204
  exit: claimedResult({
175
205
  status: "waiting_capacity",
176
206
  capacityWait: {
177
- provider: "xai",
207
+ provider,
178
208
  waiterId: armed.waiter.id,
179
209
  generation: armed.waiter.generation,
180
210
  nextCheckAt: armed.waiter.nextCheckAt.toISOString(),
@@ -190,7 +220,7 @@ export async function selectXaiTurnCapacity(
190
220
  type: "turn.failed",
191
221
  payload: {
192
222
  error,
193
- code: "xai_capacity_wait_stale",
223
+ code: provider + "_capacity_wait_stale",
194
224
  retryable: false,
195
225
  recovery: "user_message",
196
226
  },
@@ -208,28 +238,32 @@ export async function selectXaiTurnCapacity(
208
238
  control.activityStatus = "idle";
209
239
  return { exit: claimedResult({ status: "idle" }) };
210
240
  }
211
- if (leases.xai.held) leases.xai.startHeartbeat();
241
+ if (lease.held) lease.startHeartbeat();
212
242
  if (
213
243
  leased.rotationEnabled &&
214
244
  sessionPin?.pinSource !== "manual" &&
215
- (sessionPin?.pinnedCredentialId !== providerTurn.effectiveXaiCredentialId ||
245
+ (sessionPin?.pinnedCredentialId !== providerTurn[credentialKey] ||
216
246
  sessionPin?.pinSource !== "policy")
217
247
  ) {
218
- await setXaiSessionAccountPin(db, {
248
+ await setPin(db, {
219
249
  accountId: input.accountId,
220
250
  workspaceId: input.workspaceId,
221
251
  subjectId,
222
252
  sessionId: input.sessionId,
223
253
  authoritySnapshot,
224
- credentialId: providerTurn.effectiveXaiCredentialId,
254
+ credentialId: providerTurn[credentialKey],
225
255
  pinSource: "policy",
226
256
  expectedVersion: sessionPin?.version ?? null,
227
257
  }).catch((error: unknown) => {
228
- if (error instanceof Error && error.message === "xAI session pin changed") return;
258
+ if (
259
+ error instanceof Error &&
260
+ error.message === (claude ? "Claude" : "xAI") + " session pin changed"
261
+ )
262
+ return;
229
263
  throw error;
230
264
  });
231
265
  } else if (!leased.rotationEnabled && sessionPin?.pinSource === "policy") {
232
- await setXaiSessionAccountPin(db, {
266
+ await setPin(db, {
233
267
  accountId: input.accountId,
234
268
  workspaceId: input.workspaceId,
235
269
  subjectId,
@@ -239,19 +273,28 @@ export async function selectXaiTurnCapacity(
239
273
  pinSource: null,
240
274
  expectedVersion: sessionPin.version,
241
275
  }).catch((error: unknown) => {
242
- if (error instanceof Error && error.message === "xAI session pin changed") return;
276
+ if (
277
+ error instanceof Error &&
278
+ error.message === (claude ? "Claude" : "xAI") + " session pin changed"
279
+ )
280
+ return;
243
281
  throw error;
244
282
  });
245
283
  }
246
- await recordXaiSessionLastAccount(db, {
284
+ await recordLastAccount(db, {
247
285
  accountId: input.accountId,
248
286
  workspaceId: input.workspaceId,
249
287
  subjectId,
250
288
  sessionId: input.sessionId,
251
289
  authoritySnapshot,
252
- credentialId: providerTurn.effectiveXaiCredentialId,
290
+ credentialId: providerTurn[credentialKey],
253
291
  });
254
292
  }
255
293
 
256
294
  return { ok: true };
257
295
  }
296
+
297
+ export const selectXaiTurnCapacity = (deps: CapacityPhaseDeps) =>
298
+ selectScopedSubscriptionTurnCapacity(deps, "xai");
299
+ export const selectClaudeTurnCapacity = (deps: CapacityPhaseDeps) =>
300
+ selectScopedSubscriptionTurnCapacity(deps, "claude");