sneakoscope 6.4.0 → 6.7.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 (187) hide show
  1. package/README.md +26 -34
  2. package/config/codex-releases/{rust-v0.144.1.json → rust-v0.144.5.json} +5 -5
  3. package/crates/sks-core/Cargo.lock +1 -1
  4. package/crates/sks-core/Cargo.toml +1 -1
  5. package/dist/bin/install.js +1 -1
  6. package/dist/cli/command-manifest-lite.js +2 -3
  7. package/dist/cli/command-registry.js +6 -4
  8. package/dist/cli/help-fast.js +0 -1
  9. package/dist/cli/router.js +24 -3
  10. package/dist/commands/zellij.js +18 -29
  11. package/dist/config/skills-manifest.json +62 -62
  12. package/dist/core/agent-bridge/agent-manifest.js +22 -1
  13. package/dist/core/agents/agent-codex-cockpit.js +1 -81
  14. package/dist/core/agents/agent-effort-policy.js +13 -7
  15. package/dist/core/agents/agent-orchestrator.js +0 -6
  16. package/dist/core/agents/agent-output-validator.js +2 -1
  17. package/dist/core/agents/agent-patch-queue-store.js +0 -8
  18. package/dist/core/agents/agent-proof-evidence.js +0 -6
  19. package/dist/core/agents/agent-worker-pipeline.js +12 -6
  20. package/dist/core/agents/native-cli-worker-runtime.js +1 -16
  21. package/dist/core/agents/native-worker-backend-router.js +1 -1
  22. package/dist/core/bench.js +1 -1
  23. package/dist/core/codex/official-goal-mode.js +4 -2
  24. package/dist/core/codex-app/codex-app-fast-ui-repair.js +11 -17
  25. package/dist/core/codex-app/codex-app-ui-state-snapshot.js +34 -6
  26. package/dist/core/codex-app/menubar/constants.js +0 -1
  27. package/dist/core/codex-app.js +1 -1
  28. package/dist/core/codex-compat/codex-release-manifest.js +5 -5
  29. package/dist/core/codex-control/codex-0139-image-path-real-probe.js +1 -1
  30. package/dist/core/codex-control/codex-0139-web-search-probe.js +1 -1
  31. package/dist/core/codex-control/codex-control-proof.js +1 -0
  32. package/dist/core/codex-control/codex-fake-sdk-adapter.js +1 -1
  33. package/dist/core/codex-control/codex-lb-launch-recovery.js +7 -3
  34. package/dist/core/codex-control/codex-sdk-adapter.js +8 -7
  35. package/dist/core/codex-control/codex-sdk-config-policy.js +4 -24
  36. package/dist/core/codex-control/codex-sdk-env-policy.js +396 -11
  37. package/dist/core/codex-control/codex-task-runner.js +112 -57
  38. package/dist/core/codex-control/gpt-final-arbiter.js +1 -2
  39. package/dist/core/codex-control/python-codex-sdk-adapter.js +38 -15
  40. package/dist/core/codex-lb/codex-lb-tool-catalog.js +3 -3
  41. package/dist/core/codex-native/core-skill-manifest.js +4 -7
  42. package/dist/core/codex-runtime/resolve-codex-runtime.js +199 -0
  43. package/dist/core/commands/agent-bridge-command.js +46 -15
  44. package/dist/core/commands/basic-cli.js +1 -1
  45. package/dist/core/commands/command-utils.js +2 -2
  46. package/dist/core/commands/eval-command.js +19 -2
  47. package/dist/core/commands/goal-command.js +37 -86
  48. package/dist/core/commands/mad-sks-command.js +0 -2
  49. package/dist/core/commands/naruto-command.js +236 -176
  50. package/dist/core/doctor/current-project-guidance.js +1 -1
  51. package/dist/core/doctor/doctor-dirty-planner.js +1 -1
  52. package/dist/core/doctor/retired-managed-residue-missions.js +26 -11
  53. package/dist/core/doctor/retired-managed-residue-private.js +1 -1
  54. package/dist/core/doctor/retired-managed-residue-runtime.js +12 -2
  55. package/dist/core/doctor/retired-managed-residue-state.js +7 -7
  56. package/dist/core/evaluation.js +83 -21
  57. package/dist/core/feature-fixtures.js +4 -7
  58. package/dist/core/feature-registry.js +0 -1
  59. package/dist/core/fsx.js +169 -14
  60. package/dist/core/goal-workflow.js +71 -140
  61. package/dist/core/hooks-runtime/hook-io.js +2 -2
  62. package/dist/core/hooks-runtime.js +228 -50
  63. package/dist/core/init/skills.js +7 -6
  64. package/dist/core/init.js +52 -33
  65. package/dist/core/install/installed-package-smoke.js +1 -1
  66. package/dist/core/lean-engineering-policy.js +25 -23
  67. package/dist/core/locks/file-lock.js +74 -21
  68. package/dist/core/managed-assets/managed-assets-manifest.js +1 -1
  69. package/dist/core/mcp-config/health-check.js +7 -2
  70. package/dist/core/mission.js +99 -3
  71. package/dist/core/ops/upgrade-migration-fixtures.js +30 -2
  72. package/dist/core/pipeline-internals/runtime-core.js +67 -95
  73. package/dist/core/pipeline-internals/runtime-gates.js +25 -6
  74. package/dist/core/proof/fake-real-proof-policy.js +32 -9
  75. package/dist/core/proof/route-proof-gate.js +49 -1
  76. package/dist/core/provider/model-router.js +2 -0
  77. package/dist/core/questions.js +31 -5
  78. package/dist/core/recallpulse.js +2 -2
  79. package/dist/core/release/canonical-test-proof.js +135 -0
  80. package/dist/core/release/release-closure-contract.js +1 -0
  81. package/dist/core/release/release-closure-validation.js +25 -12
  82. package/dist/core/release/release-closure.js +34 -5
  83. package/dist/core/release/release-gate-contract.js +4 -3
  84. package/dist/core/release/release-gate-dag.js +4 -2
  85. package/dist/core/release/release-pack-content-scanner.js +7 -6
  86. package/dist/core/release/release-pack-receipt.js +33 -12
  87. package/dist/core/release/release-real-contract.js +41 -2
  88. package/dist/core/retention.js +95 -16
  89. package/dist/core/routes/constants.js +1 -1
  90. package/dist/core/routes/dollar-manifest-lite.js +1 -1
  91. package/dist/core/routes.js +18 -20
  92. package/dist/core/safety/command-contract/contracts.js +33 -0
  93. package/dist/core/safety/command-contract/types.js +1 -1
  94. package/dist/core/safety/ssot-guard.js +1 -54
  95. package/dist/core/stop-gate/stop-gate-check.js +0 -14
  96. package/dist/core/stop-gate/stop-gate-writer.js +0 -4
  97. package/dist/core/strategy/adhd-orchestrating-gate.js +2 -2
  98. package/dist/core/subagents/agent-catalog.js +28 -5
  99. package/dist/core/subagents/model-policy.js +52 -11
  100. package/dist/core/subagents/naruto-help-contract.js +2 -1
  101. package/dist/core/subagents/naruto-proof-projection.js +449 -0
  102. package/dist/core/subagents/official-subagent-preparation.js +641 -51
  103. package/dist/core/subagents/official-subagent-prompt.js +16 -6
  104. package/dist/core/subagents/official-subagent-runner.js +132 -12
  105. package/dist/core/subagents/subagent-evidence.js +44 -8
  106. package/dist/core/subagents/wave-lifecycle.js +238 -0
  107. package/dist/core/update-check.js +13 -4
  108. package/dist/core/verification/machine-feedback.js +39 -19
  109. package/dist/core/version.js +1 -1
  110. package/dist/core/zellij/zellij-lane-renderer.js +19 -19
  111. package/dist/core/zellij/zellij-official-subagent-activity.js +2 -0
  112. package/dist/core/zellij/zellij-right-column-manager.js +6 -55
  113. package/dist/core/zellij/zellij-slot-column-anchor.js +4 -5
  114. package/dist/core/zellij/zellij-slot-pane-renderer.js +1 -1
  115. package/dist/core/zellij/zellij-ui-mode.js +0 -7
  116. package/dist/core/zellij/zellij-worker-pane-manager.js +3 -11
  117. package/dist/native/sks-menubar/Sources/AppDelegate.swift +0 -1
  118. package/dist/native/sks-menubar/Sources/NotificationCoordinator.swift +1 -3
  119. package/dist/native/sks-menubar/Sources/OverviewViewController.swift +194 -24
  120. package/dist/native/sks-menubar/Sources/ProcessClient.swift +49 -4
  121. package/dist/native/sks-menubar/Sources/ProvidersViewController.swift +38 -10
  122. package/dist/native/sks-menubar/Sources/StatusItemController.swift +73 -11
  123. package/dist/native/sks-menubar/Sources/UpdatesViewController.swift +27 -2
  124. package/dist/scripts/architecture-guard-check.js +1 -9
  125. package/dist/scripts/canonical-test-runner.js +51 -8
  126. package/dist/scripts/check-architecture.js +11 -1
  127. package/dist/scripts/cli-output-consistency-check.js +0 -2
  128. package/dist/scripts/codex-0144-app-server-v2-check.js +4 -4
  129. package/dist/scripts/codex-0144-binary-identity-check.js +10 -4
  130. package/dist/scripts/codex-0144-capability-check.js +5 -5
  131. package/dist/scripts/codex-0144-policy-check.js +4 -0
  132. package/dist/scripts/codex-control-all-pipelines-check.js +2 -1
  133. package/dist/scripts/codex-lb-gpt56-fast-profile-check.js +3 -3
  134. package/dist/scripts/codex-sdk-all-pipelines-check.js +2 -1
  135. package/dist/scripts/codex-sdk-real-smoke-check.js +20 -2
  136. package/dist/scripts/current-command-surface-check.js +5 -3
  137. package/dist/scripts/current-surface-update-e2e-check.js +2 -2
  138. package/dist/scripts/docs-truthfulness-check.js +8 -6
  139. package/dist/scripts/doctor-fixes-codex-app-fast-ui-check.js +3 -2
  140. package/dist/scripts/gate-policy-audit-check.js +7 -1
  141. package/dist/scripts/harness-benchmark-check.js +4 -4
  142. package/dist/scripts/hook-latency-quantum-check.js +2 -2
  143. package/dist/scripts/legacy-gate-purge-check.js +4 -2
  144. package/dist/scripts/loop-directive-check-lib.js +14 -13
  145. package/dist/scripts/naruto-codex-e2e-check.js +2 -2
  146. package/dist/scripts/naruto-ssot-gate-aliases-check.js +9 -0
  147. package/dist/scripts/naruto-ssot-pipeline-default-check.js +10 -0
  148. package/dist/scripts/naruto-ssot-route-normalization-check.js +8 -0
  149. package/dist/scripts/naruto-ssot-routing-check.js +12 -0
  150. package/dist/scripts/product-design-plugin-routing-check.js +4 -9
  151. package/dist/scripts/release-affected-selector-check.js +7 -1
  152. package/dist/scripts/release-check-stamp.js +151 -18
  153. package/dist/scripts/release-dynamic-presets-check.js +5 -2
  154. package/dist/scripts/release-metadata-1-19-check.js +4 -0
  155. package/dist/scripts/release-real-check.js +21 -3
  156. package/dist/scripts/sks-menubar-install-check.js +5 -5
  157. package/dist/scripts/upgrade-migration-matrix-check.js +278 -5
  158. package/dist/scripts/zellij-developer-controls-check.js +3 -5
  159. package/dist/scripts/zellij-initial-main-only-blackbox.js +3 -8
  160. package/dist/scripts/zellij-pane-lock-open-worker-integration-blackbox.js +1 -2
  161. package/dist/scripts/zellij-right-column-headless-overflow-check.js +1 -1
  162. package/dist/scripts/zellij-right-column-manager-check.js +3 -4
  163. package/dist/scripts/zellij-slot-only-ui-check.js +2 -2
  164. package/dist/scripts/zellij-stacked-fallback-integration-blackbox.js +1 -2
  165. package/docs/demo.tape +1 -1
  166. package/infra-harness-gates.json +0 -27
  167. package/package.json +11 -6
  168. package/release-gates.v2.json +150 -22
  169. package/schemas/codex/agent-result.schema.json +4 -0
  170. package/schemas/codex/app-server-0.144/codex_app_server_protocol.v2.schemas.json +1 -18812
  171. package/schemas/codex/codex-0139-real-probe-result.schema.json +2 -2
  172. package/schemas/zellij/zellij-right-column-state.schema.json +0 -1
  173. package/dist/core/commands/ui-command.js +0 -198
  174. package/dist/core/loops/goal-to-loop-compat.js +0 -22
  175. package/dist/core/naruto/naruto-allocation-policy.js +0 -98
  176. package/dist/core/naruto/naruto-finalizer.js +0 -22
  177. package/dist/core/naruto/naruto-gpt-final-pack.js +0 -50
  178. package/dist/core/naruto/naruto-real-worker-child.js +0 -209
  179. package/dist/core/naruto/naruto-real-worker-runtime.js +0 -178
  180. package/dist/core/naruto/naruto-rebalance-policy.js +0 -47
  181. package/dist/core/naruto/naruto-verification-pool.js +0 -17
  182. package/dist/core/ui/dashboard-html.js +0 -110
  183. package/dist/core/zellij/zellij-dashboard-pane.js +0 -70
  184. package/dist/core/zellij/zellij-dashboard-renderer.js +0 -59
  185. package/dist/core/zellij/zellij-naruto-dashboard.js +0 -44
  186. package/dist/scripts/zellij-dashboard-pane-check.js +0 -69
  187. package/dist/scripts/zellij-dashboard-watch.js +0 -40
@@ -19,6 +19,7 @@ import { runLocalLlmTask } from '../local-llm/local-llm-control-adapter.js';
19
19
  import { detectPythonCodexSdkCapability, runPythonCodexSdkTask } from './python-codex-sdk-adapter.js';
20
20
  import { defaultModelCallBudget, withModelCallSlot } from './model-call-concurrency.js';
21
21
  import { inspectCodexLbSdkLaunchRecovery } from './codex-lb-launch-recovery.js';
22
+ import { prepareNativeCodexAuthBridge } from './codex-sdk-env-policy.js';
22
23
  export async function runCodexTask(input) {
23
24
  const root = path.resolve(input.mutationLedgerRoot);
24
25
  await ensureDir(root);
@@ -41,6 +42,12 @@ export async function runCodexTask(input) {
41
42
  await ensureDir(runtime.env.env.HOME);
42
43
  if (runtime.env.env.CODEX_HOME)
43
44
  await ensureDir(runtime.env.env.CODEX_HOME);
45
+ const fakeAllowed = fakeCodexSdkAllowed();
46
+ const nativeCodexAuthBridge = await prepareNativeCodexAuthBridge(runtime.env.env, { required: !fakeAllowed });
47
+ if (nativeCodexAuthBridge.ok) {
48
+ runtime.env.proof.home = runtime.env.env.HOME;
49
+ runtime.env.proof.codex_home = runtime.env.env.CODEX_HOME;
50
+ }
44
51
  const codexLbToolOutputRecovery = await inspectCodexLbSdkLaunchRecovery({
45
52
  config: runtime.config,
46
53
  env: runtime.env.env,
@@ -48,44 +55,50 @@ export async function runCodexTask(input) {
48
55
  });
49
56
  if (codexLbToolOutputRecovery.ok)
50
57
  await ensurePythonCodexLbConfig(runtime.env.env, runtime.config);
51
- const fakeAllowed = fakeCodexSdkAllowed();
52
58
  const blockers = [
53
59
  ...(capability.ok || fakeAllowed ? [] : capability.blockers),
54
60
  ...(sandbox.ok ? [] : sandbox.blockers),
61
+ ...(nativeCodexAuthBridge.ok ? [] : nativeCodexAuthBridge.blockers),
55
62
  ...(codexLbToolOutputRecovery.ok ? [] : codexLbToolOutputRecovery.blockers)
56
63
  ];
57
64
  let adapterResult = null;
58
- if (!blockers.length) {
59
- adapterResult = await withModelCallSlot({
60
- root,
61
- missionId: task.missionId,
62
- provider: 'codex-sdk',
63
- budget: defaultModelCallBudget('codex-sdk'),
64
- slotId: task.slotId || null,
65
- generationIndex: task.generationIndex ?? null,
66
- sessionId: task.sessionId || null,
67
- backend: 'codex-sdk'
68
- }, () => runWithCodexReliabilityShield(task, async (_attempt, controls) => {
69
- try {
70
- const attemptTask = controls?.noMcp
71
- ? { ...task, requestedScopeContract: { ...task.requestedScopeContract, no_mcp: true } }
72
- : task;
73
- return fakeAllowed
74
- ? await runFakeCodexSdkTask(attemptTask)
75
- : await runRealCodexSdkTask(attemptTask, { sandboxMode: sandbox.sandboxMode, env: runtime.env.env, config: { ...runtime.config, mcp_servers: {} } });
76
- }
77
- catch (err) {
78
- return {
79
- ok: false,
80
- sdkThreadId: '',
81
- sdkRunId: null,
82
- events: [],
83
- finalResponse: '',
84
- structuredOutput: null,
85
- blockers: ['codex_sdk_run_failed:' + String(err?.message || err)]
86
- };
87
- }
88
- }));
65
+ let nativeAuthCleanupBlockers = [];
66
+ try {
67
+ if (!blockers.length) {
68
+ adapterResult = await withModelCallSlot({
69
+ root,
70
+ missionId: task.missionId,
71
+ provider: 'codex-sdk',
72
+ budget: defaultModelCallBudget('codex-sdk'),
73
+ slotId: task.slotId || null,
74
+ generationIndex: task.generationIndex ?? null,
75
+ sessionId: task.sessionId || null,
76
+ backend: 'codex-sdk'
77
+ }, () => runWithCodexReliabilityShield(task, async (_attempt, controls) => {
78
+ try {
79
+ const attemptTask = controls?.noMcp
80
+ ? { ...task, requestedScopeContract: { ...task.requestedScopeContract, no_mcp: true } }
81
+ : task;
82
+ return fakeAllowed
83
+ ? await runFakeCodexSdkTask(attemptTask)
84
+ : await runRealCodexSdkTask(attemptTask, { sandboxMode: sandbox.sandboxMode, env: runtime.env.env, config: { ...runtime.config, mcp_servers: {} } });
85
+ }
86
+ catch (err) {
87
+ return {
88
+ ok: false,
89
+ sdkThreadId: '',
90
+ sdkRunId: null,
91
+ events: [],
92
+ finalResponse: '',
93
+ structuredOutput: null,
94
+ blockers: ['codex_sdk_run_failed:' + String(err?.message || err)]
95
+ };
96
+ }
97
+ }));
98
+ }
99
+ }
100
+ finally {
101
+ nativeAuthCleanupBlockers = await cleanupNativeCodexAuthBridge(nativeCodexAuthBridge);
89
102
  }
90
103
  const events = Array.isArray(adapterResult?.events) ? adapterResult.events : [];
91
104
  const translatedEvents = translateCodexSdkEvents(events);
@@ -99,6 +112,7 @@ export async function runCodexTask(input) {
99
112
  const validation = structuredOutput ? validateJsonSchemaRecursive(structuredOutput, schema) : { ok: false, issues: ['structured_output_missing'] };
100
113
  const primaryBlockers = [
101
114
  ...blockers,
115
+ ...nativeAuthCleanupBlockers,
102
116
  ...(adapterResult?.blockers || []),
103
117
  ...codexControlAdapterFailureBlockers(adapterResult, 'codex-sdk')
104
118
  ];
@@ -133,6 +147,7 @@ export async function runCodexTask(input) {
133
147
  backend_family: fakeAllowed ? 'fake' : 'remote-gpt',
134
148
  sdkThreadId: String(adapterResult?.sdkThreadId || ''),
135
149
  sdkRunId: adapterResult?.sdkRunId ? String(adapterResult.sdkRunId) : null,
150
+ runtimeIdentity: adapterResult?.runtimeIdentity || null,
136
151
  streamEventCount: events.length,
137
152
  structuredOutputValid: validation.ok,
138
153
  workerResultPath,
@@ -174,6 +189,7 @@ export async function runCodexTask(input) {
174
189
  ...runtime.env.proof,
175
190
  capacity_fallback_selected: result.capacityFallback === true,
176
191
  model_capacity_retry_count: result.modelCapacityRetryCount,
192
+ native_codex_auth_bridge: nativeCodexAuthBridge.proof,
177
193
  codex_lb_tool_output_recovery: codexLbToolOutputRecovery
178
194
  },
179
195
  config: runtime.config,
@@ -190,36 +206,49 @@ async function runPythonControlTask(root, task, schema, routerDecision) {
190
206
  await ensureDir(runtime.env.env.HOME);
191
207
  if (runtime.env.env.CODEX_HOME)
192
208
  await ensureDir(runtime.env.env.CODEX_HOME);
209
+ const fakeAllowed = process.env.SKS_PYTHON_CODEX_SDK_FAKE === '1';
210
+ const nativeCodexAuthBridge = await prepareNativeCodexAuthBridge(runtime.env.env, { required: !fakeAllowed });
211
+ if (nativeCodexAuthBridge.ok) {
212
+ runtime.env.proof.home = runtime.env.env.HOME;
213
+ runtime.env.proof.codex_home = runtime.env.env.CODEX_HOME;
214
+ }
193
215
  const codexLbToolOutputRecovery = await inspectCodexLbSdkLaunchRecovery({
194
216
  config: runtime.config,
195
217
  env: runtime.env.env,
196
218
  overrideEnv: process.env
197
219
  });
198
- const fakeAllowed = process.env.SKS_PYTHON_CODEX_SDK_FAKE === '1';
199
- const adapterResult = codexLbToolOutputRecovery.ok && (capability.ok || fakeAllowed)
200
- ? await withModelCallSlot({
201
- root,
202
- missionId: task.missionId,
203
- provider: 'python-codex-sdk',
204
- budget: defaultModelCallBudget('python-codex-sdk'),
205
- slotId: task.slotId || null,
206
- generationIndex: task.generationIndex ?? null,
207
- sessionId: task.sessionId || null,
208
- backend: 'python-codex-sdk'
209
- }, () => runPythonCodexSdkTask(task, { env: runtime.env.env, config: runtime.config }))
210
- : {
211
- ok: false,
212
- events: [],
213
- translatedEvents: [],
214
- finalResponse: '',
215
- threadId: '',
216
- turnId: '',
217
- blockers: [
218
- ...(codexLbToolOutputRecovery.ok ? [] : codexLbToolOutputRecovery.blockers),
219
- ...(capability.ok || fakeAllowed ? [] : capability.blockers)
220
- ],
221
- capability
222
- };
220
+ let adapterResult;
221
+ let nativeAuthCleanupBlockers = [];
222
+ try {
223
+ adapterResult = codexLbToolOutputRecovery.ok && nativeCodexAuthBridge.ok && (capability.ok || fakeAllowed)
224
+ ? await withModelCallSlot({
225
+ root,
226
+ missionId: task.missionId,
227
+ provider: 'python-codex-sdk',
228
+ budget: defaultModelCallBudget('python-codex-sdk'),
229
+ slotId: task.slotId || null,
230
+ generationIndex: task.generationIndex ?? null,
231
+ sessionId: task.sessionId || null,
232
+ backend: 'python-codex-sdk'
233
+ }, () => runPythonCodexSdkTask(task, { env: runtime.env.env, config: runtime.config }))
234
+ : {
235
+ ok: false,
236
+ events: [],
237
+ translatedEvents: [],
238
+ finalResponse: '',
239
+ threadId: '',
240
+ turnId: '',
241
+ blockers: [
242
+ ...(codexLbToolOutputRecovery.ok ? [] : codexLbToolOutputRecovery.blockers),
243
+ ...(nativeCodexAuthBridge.ok ? [] : nativeCodexAuthBridge.blockers),
244
+ ...(capability.ok || fakeAllowed ? [] : capability.blockers)
245
+ ],
246
+ capability
247
+ };
248
+ }
249
+ finally {
250
+ nativeAuthCleanupBlockers = await cleanupNativeCodexAuthBridge(nativeCodexAuthBridge);
251
+ }
223
252
  const events = Array.isArray(adapterResult.events) ? adapterResult.events : [];
224
253
  const translatedEvents = Array.isArray(adapterResult.translatedEvents) ? adapterResult.translatedEvents : [];
225
254
  for (const event of translatedEvents)
@@ -227,6 +256,7 @@ async function runPythonControlTask(root, task, schema, routerDecision) {
227
256
  const structuredOutput = parseStructuredOutput(adapterResult.finalResponse || '');
228
257
  const validation = structuredOutput ? validateJsonSchemaRecursive(structuredOutput, schema) : { ok: false, issues: ['structured_output_missing'] };
229
258
  const primaryBlockers = [
259
+ ...nativeAuthCleanupBlockers,
230
260
  ...(adapterResult.blockers || []),
231
261
  ...codexControlAdapterFailureBlockers(adapterResult, 'python-codex-sdk')
232
262
  ];
@@ -268,6 +298,7 @@ async function runPythonControlTask(root, task, schema, routerDecision) {
268
298
  stream_event_count: events.length,
269
299
  structured_output_valid: validation.ok,
270
300
  worker_result_path: workerResultPath,
301
+ native_codex_auth_bridge: nativeCodexAuthBridge.proof,
271
302
  codex_lb_tool_output_recovery: codexLbToolOutputRecovery,
272
303
  blockers: finalBlockers
273
304
  });
@@ -317,6 +348,7 @@ async function runPythonControlTask(root, task, schema, routerDecision) {
317
348
  ...runtime.env.proof,
318
349
  python_bin: capability.python_bin,
319
350
  python_version: capability.python_version,
351
+ native_codex_auth_bridge: nativeCodexAuthBridge.proof,
320
352
  codex_lb_tool_output_recovery: codexLbToolOutputRecovery
321
353
  },
322
354
  config: { ...runtime.config, backend: 'python-codex-sdk', package_name: capability.package_name, import_name: capability.import_name },
@@ -326,6 +358,27 @@ async function runPythonControlTask(root, task, schema, routerDecision) {
326
358
  });
327
359
  return result;
328
360
  }
361
+ async function cleanupNativeCodexAuthBridge(bridge) {
362
+ const proof = bridge.proof;
363
+ try {
364
+ const cleanup = await bridge.cleanup();
365
+ proof.cleanup_required = cleanup.cleanup_required;
366
+ proof.cleanup_status = cleanup.status;
367
+ proof.cleanup_outcome = cleanup.outcome;
368
+ if (!cleanup.ok) {
369
+ proof.cleanup_blockers = cleanup.blockers;
370
+ return cleanup.blockers;
371
+ }
372
+ return [];
373
+ }
374
+ catch (error) {
375
+ const blocker = `native_codex_auth_cleanup_failed:${String(error?.message || error)}`;
376
+ proof.cleanup_required = true;
377
+ proof.cleanup_status = 'failed';
378
+ proof.cleanup_blockers = [blocker];
379
+ return [blocker];
380
+ }
381
+ }
329
382
  async function runLocalControlTask(root, task, schema, routerDecision) {
330
383
  const config = await readLocalModelConfig();
331
384
  const adapterResult = await withModelCallSlot({
@@ -489,6 +542,8 @@ function isRunFailureBlocker(blockers) {
489
542
  || text.startsWith('python_codex_sdk_run_failed')
490
543
  || text.startsWith('python_codex_sdk_timeout')
491
544
  || text.startsWith('python_codex_sdk_error')
545
+ || text.startsWith('native_codex_auth_bridge_failed')
546
+ || text.startsWith('native_codex_auth_cleanup_failed')
492
547
  || text.startsWith('local_llm_generate_failed')
493
548
  || text.startsWith('local_llm_eligibility_blocked')
494
549
  || text.startsWith('codex_lb_tool_output_recovery_')
@@ -147,8 +147,7 @@ function buildArbiterPrompt(input, compressed) {
147
147
  'You are the GPT Final Arbiter for an SKS local collaboration run.',
148
148
  'Local model outputs are drafts only. Review the proof pack, candidate diff, patch envelopes, verification results, side effects, mutation ledger, and rollback plan.',
149
149
  leanEngineeringCompactText(),
150
- 'Lean review: check for reused helpers before reimplementation, unjustified dependencies, one-implementation factories/interfaces, hidden mock or provider fallbacks, duplicated caller guards instead of root-cause fixes, forwarding-only files, missing runnable checks for non-trivial logic, and safety/validation removal disguised as simplification.',
151
- 'Approve or modify only when the candidate is safe, supported, and no more complex than the request requires. Reject unsafe local patches. Return only the requested structured JSON schema.',
150
+ 'Judge the candidate against that directive and the recorded evidence. Reject fabricated substitutes, unsupported complexity, or unsafe changes. Return only the requested structured JSON schema.',
152
151
  JSON.stringify({
153
152
  route: input.route,
154
153
  mission_id: input.mission_id,
@@ -1,6 +1,6 @@
1
1
  import { spawn } from 'node:child_process';
2
2
  import path from 'node:path';
3
- import { packageRoot, randomId, runProcess, which } from '../fsx.js';
3
+ import { packageRoot, randomId, registerDetachedProcessGroup, runProcess, which } from '../fsx.js';
4
4
  import { translatePythonCodexSdkEvents } from './python-codex-sdk-event-translator.js';
5
5
  export async function detectPythonCodexSdkCapability() {
6
6
  const python = await resolvePythonCodexSdkPython();
@@ -88,10 +88,13 @@ export async function runPythonCodexSdkTask(input, opts = {}) {
88
88
  }
89
89
  function pythonRunnerEnv(envOverride, moduleParentPath) {
90
90
  const env = {};
91
- for (const [key, value] of Object.entries(envOverride || process.env)) {
91
+ for (const [key, value] of Object.entries(envOverride || {})) {
92
92
  if (value !== undefined)
93
93
  env[key] = String(value);
94
94
  }
95
+ if (process.env.SKS_PYTHON_CODEX_SDK_FAKE === '1' && env.SKS_PYTHON_CODEX_SDK_FAKE === undefined) {
96
+ env.SKS_PYTHON_CODEX_SDK_FAKE = '1';
97
+ }
95
98
  const parent = String(moduleParentPath || '').trim();
96
99
  if (!parent)
97
100
  return env;
@@ -102,21 +105,29 @@ function prependPath(value, entry) {
102
105
  const parts = String(value || '').split(path.delimiter).filter(Boolean);
103
106
  return [entry, ...parts.filter((part) => part !== entry)].join(path.delimiter);
104
107
  }
105
- function runPythonRunner(python, request, envOverride, timeoutMs) {
108
+ export function runPythonRunner(python, request, envOverride, timeoutMs, forceKillDelayMs = 5000) {
106
109
  const runner = path.join(packageRoot(), 'pytools', 'codex_sdk_runner.py');
107
110
  return new Promise((resolve, reject) => {
108
111
  const child = spawn(python, [runner], {
109
112
  stdio: ['pipe', 'pipe', 'pipe'],
110
- env: envOverride ? { ...process.env, ...envOverride } : process.env,
113
+ env: envOverride || {},
111
114
  detached: process.platform !== 'win32'
112
115
  });
116
+ const unregisterDetachedProcessGroup = registerDetachedProcessGroup(child);
113
117
  const events = [];
114
118
  let stderr = '';
115
119
  let timedOut = false;
120
+ let settled = false;
121
+ let cancelForceKill = () => { };
122
+ const cleanupLifecycle = () => {
123
+ clearTimeout(timer);
124
+ cancelForceKill();
125
+ unregisterDetachedProcessGroup();
126
+ };
116
127
  const timer = setTimeout(() => {
117
128
  timedOut = true;
118
129
  events.push({ event: 'error', retryable: true, message: `python_codex_sdk_timeout:${timeoutMs}` });
119
- terminatePythonRunner(child);
130
+ cancelForceKill = terminatePythonRunner(child, forceKillDelayMs);
120
131
  }, timeoutMs);
121
132
  timer.unref?.();
122
133
  child.stdout.setEncoding('utf8');
@@ -132,9 +143,18 @@ function runPythonRunner(python, request, envOverride, timeoutMs) {
132
143
  }
133
144
  });
134
145
  child.stderr.on('data', (chunk) => { stderr += String(chunk); });
135
- child.on('error', reject);
136
- child.on('close', () => {
137
- clearTimeout(timer);
146
+ child.once('error', (error) => {
147
+ if (settled)
148
+ return;
149
+ settled = true;
150
+ cleanupLifecycle();
151
+ reject(error);
152
+ });
153
+ child.once('close', () => {
154
+ if (settled)
155
+ return;
156
+ settled = true;
157
+ cleanupLifecycle();
138
158
  if (stderr.trim())
139
159
  events.push({ event: 'stderr', message: stderr.slice(-1000) });
140
160
  if (timedOut && !events.some((event) => String(event?.message || '').startsWith('python_codex_sdk_timeout:'))) {
@@ -159,12 +179,13 @@ function positiveFinite(value) {
159
179
  const parsed = Number(value);
160
180
  return Number.isFinite(parsed) && parsed > 0 ? parsed : null;
161
181
  }
162
- function terminatePythonRunner(child) {
163
- if (!child.pid)
164
- return;
182
+ function terminatePythonRunner(child, forceKillDelayMs) {
183
+ const pid = child.pid;
184
+ if (!pid)
185
+ return () => { };
165
186
  try {
166
187
  if (process.platform !== 'win32')
167
- process.kill(-child.pid, 'SIGTERM');
188
+ process.kill(-pid, 'SIGTERM');
168
189
  else
169
190
  child.kill('SIGTERM');
170
191
  }
@@ -174,15 +195,17 @@ function terminatePythonRunner(child) {
174
195
  }
175
196
  catch { }
176
197
  }
177
- setTimeout(() => {
198
+ const forceKillTimer = setTimeout(() => {
178
199
  try {
179
200
  if (process.platform !== 'win32')
180
- process.kill(-child.pid, 'SIGKILL');
201
+ process.kill(-pid, 'SIGKILL');
181
202
  else
182
203
  child.kill('SIGKILL');
183
204
  }
184
205
  catch { }
185
- }, 5000).unref?.();
206
+ }, forceKillDelayMs);
207
+ forceKillTimer.unref?.();
208
+ return () => clearTimeout(forceKillTimer);
186
209
  }
187
210
  function mapSandbox(value) {
188
211
  if (value === 'workspace-write')
@@ -26,7 +26,7 @@ const REQUIRED_CODEX_0144_MODEL_FIELDS = {
26
26
  supports_parallel_tool_calls: ['boolean'],
27
27
  experimental_supported_tools: ['array']
28
28
  };
29
- // Exact union observed in Codex CLI 0.144.1's native cache and codex-lb catalog.
29
+ // Exact union observed in Codex CLI 0.144.5's native cache and codex-lb catalog.
30
30
  // Unknown response fields are deliberately not persisted into a Codex-owned file.
31
31
  const CODEX_0144_MODEL_FIELD_TYPES = {
32
32
  ...REQUIRED_CODEX_0144_MODEL_FIELDS,
@@ -94,7 +94,7 @@ export function normalizeCodexLbToolCatalog(payload, opts = {}) {
94
94
  return sanitized;
95
95
  if (row.use_responses_lite !== false)
96
96
  patchedModels.push(model);
97
- // Codex 0.144.1 omits the request's `tools` field for Responses Lite.
97
+ // Codex 0.144.5 omits the request's `tools` field for Responses Lite.
98
98
  // Preserve the provider's tool_mode contract, but force full Responses.
99
99
  return { ...sanitized, use_responses_lite: false };
100
100
  });
@@ -393,7 +393,7 @@ function catalogIdentity(baseUrl, apiKey) {
393
393
  origin: new URL(baseUrl).origin,
394
394
  base_url_sha256: sha256(baseUrl),
395
395
  api_key_sha256: sha256(apiKey),
396
- contract: 'codex-cli-0.144.1-model-catalog'
396
+ contract: 'codex-cli-0.144.5-model-catalog'
397
397
  };
398
398
  }
399
399
  function sameCatalogIdentity(actual, expected) {
@@ -1,5 +1,5 @@
1
1
  import { PACKAGE_VERSION, nowIso, sha256 } from '../fsx.js';
2
- import { leanPolicyReference } from '../lean-engineering-policy.js';
2
+ import { coreEngineeringDirectiveReference } from '../lean-engineering-policy.js';
3
3
  import { normalizeDollarSkillName, prefixKnownSksDollarReferences, sksPrefixedDollarCommand, sksPrefixedSkillName } from '../routes/dollar-prefix.js';
4
4
  import { canonicalSkillName } from './skill-name-canonicalizer.js';
5
5
  export const CORE_SKILL_TEMPLATE_VERSION = 'sks-core-skill-template.v1';
@@ -23,7 +23,7 @@ const CORE_SKILL_DEFINITIONS = [
23
23
  route: '$Naruto',
24
24
  purpose: 'run a Codex official subagent workflow with official agent threads while parent integration remains owner.',
25
25
  when: 'Use when the user explicitly invokes $Naruto or the selected route requires bounded parallel delegation.',
26
- workflow: 'Use sks naruto run "<task>" [--agents N] [--max-threads N] [--json]. Naruto is the default execution route for non-trivial change requests; Answer and truly tiny DFix work stay lightweight. Automatic fan-out starts at two for bounded work, four for explicit parallel work, and six for large-scale work, then may expand to ten only after decomposition proves useful independent slices. Before every wave compute C_t as the minimum of ready DAG width, disjoint ownership, verifier capacity, tool concurrency, available slots after parent/reviewer reservations, and workers with positive marginal usefulness; max_threads is a cap, never a target. An explicit operator --agents N remains authoritative. The GPT-5.6 Sol Max parent selects the narrow project-scoped custom role matching each slice. Luna Max is only for tiny short-context mechanical work; Sol High handles ordinary implementation; Sol Max handles review, debugging, planning, architecture, security, DB, research, release, ambiguity, and judgment; Terra Medium handles long-context analysis plus direct Computer Use, Browser/Chrome, and image-generation execution. Split mixed execution and judgment where safe; otherwise Sol Max wins. Reject duplicate slice fingerprints and overlapping or unassigned parallel writes. Reviewer-only fan-out is capped at two ordinarily and three for critical multi-domain review; protected security/DB/release/irreversible gates cannot be offset by aggregate gains. Keep max_depth=1, wait for every requested subagent, reuse only four ordinary or six complex query-aware TriWiki trust/hydration anchors, treat SubagentStart/SubagentStop as lifecycle-only evidence, require subagent-parent-summary.json with one structured outcome per thread, and let the parent own integration and final judgment.',
26
+ workflow: 'Run sks naruto run "<task>" [--agents N] [--max-threads N] [--json] with Codex official subagent threads only. The parent owns decomposition, per-wave capacity, later root-owned waves, integration, and final verification. Automatic targets begin at 2/4/6 by task size and may expand to 10 only for independent useful slices; max_threads is a cap, never a target, and max_depth=1 blocks nested delegation. Route each slice to the narrowest matching Codex role and wait for every planned thread before final.',
27
27
  safety: 'Preserve user-authored content, inherit the parent permission mode, do not spawn nested subagents, do not inject the full pack or the full TriWiki context into every child, and do not fall back to another model, process runtime, custom scheduler, or worker pool. The historical Naruto process runtime is removed; stop with explicit blocker evidence when the official path is unavailable.',
28
28
  cli: 'sks naruto run "<task>" [--agents N] [--max-threads N] [--json]; sks naruto status|subagents|proof [--mission <id>] [--json]',
29
29
  evidence: 'subagent-plan.json, subagent-events.jsonl, subagent-parent-summary.json, subagent-evidence.json, naruto-summary.json, and naruto-gate.json.',
@@ -157,7 +157,7 @@ export function renderCoreSkillTemplate(name) {
157
157
  if (!legacy)
158
158
  throw new Error(`Unknown SKS core skill: ${name}`);
159
159
  const skill = currentCoreSkillDefinition(legacy);
160
- const lean = leanPolicyReference();
160
+ const directive = coreEngineeringDirectiveReference();
161
161
  return [
162
162
  '---',
163
163
  `name: ${skill.display_name}`,
@@ -180,13 +180,10 @@ export function renderCoreSkillTemplate(name) {
180
180
  `Use when: ${skill.when}`,
181
181
  `Workflow: ${skill.workflow || 'Run the selected route lifecycle, read source evidence before mutation planning, keep changes scoped, verify with the cheapest sufficient check, and record blockers honestly.'}`,
182
182
  `CLI entrypoint: ${skill.cli || skill.route}`,
183
- `Lean policy: ${lean.policy_id}/${lean.policy_hash}`,
183
+ `Core directive: ${directive.directive_id}/${directive.directive_hash}`,
184
184
  `Safety: ${skill.safety || 'Preserve user-authored content, keep route state bounded, avoid unsupported guarantees, and stop on hard blockers instead of fabricating fallback behavior.'}`,
185
185
  `Evidence/artifacts: ${skill.evidence}`,
186
- `Proof paths: ${skill.evidence}`,
187
- 'Safety rules: preserve user-authored skills, keep route state bounded, and stop on hard blockers instead of fabricating fallback behavior.',
188
186
  `Failure/recovery: ${skill.fallback}`,
189
- `Failure recovery: ${skill.fallback}`,
190
187
  ''
191
188
  ].join('\n');
192
189
  }