@fitlab-ai/agent-infra 0.9.9 → 0.9.11

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 (309) hide show
  1. package/README.md +13 -3
  2. package/README.zh-CN.md +13 -3
  3. package/bin/cli.ts +17 -4
  4. package/dist/bin/cli.js +19 -4
  5. package/dist/bin/internal-cli.js +55 -4
  6. package/dist/lib/agent-client.js +0 -1
  7. package/dist/lib/agent-clients/adapters/codex-lifecycle/build-identity.js +17 -10
  8. package/dist/lib/agent-clients/adapters/codex-lifecycle/controller-context.js +11 -31
  9. package/dist/lib/agent-clients/adapters/codex-lifecycle/sandbox-controller.js +15 -33
  10. package/dist/lib/agent-clients/adapters/codex-sandbox.js +72 -11
  11. package/dist/lib/agent-clients/adapters/index.js +3 -1
  12. package/dist/lib/agent-clients/adapters/opencode-sandbox.js +0 -4
  13. package/dist/lib/agent-clients/adapters/traecli.js +65 -0
  14. package/dist/lib/agent-clients/config.js +14 -99
  15. package/dist/lib/agent-clients/reconcile.js +1 -11
  16. package/dist/lib/agent-clients/schema.js +5 -4
  17. package/dist/lib/agent-clients/tokens.js +7 -17
  18. package/dist/lib/agent-clients/types.js +2 -1
  19. package/dist/lib/decide.js +14 -30
  20. package/dist/lib/defaults.json +9 -0
  21. package/dist/lib/init.js +2 -2
  22. package/dist/lib/internal/codex-lifecycle.js +2 -2
  23. package/dist/lib/internal/codex-sandbox-controller.js +4 -3
  24. package/dist/lib/internal/release-workflow.js +0 -1
  25. package/dist/lib/internal/sandbox-control.js +2 -2
  26. package/dist/lib/internal/task-finalization.js +19 -9
  27. package/dist/lib/internal/task-ledger.js +8 -2
  28. package/dist/lib/internal/task-lifecycle.js +17 -93
  29. package/dist/lib/internal/task-orchestration.js +30 -216
  30. package/dist/lib/{task/commands/validate.js → internal/task-validate.js} +77 -43
  31. package/dist/lib/merge.js +205 -103
  32. package/dist/lib/process-data/normalize.js +2 -9
  33. package/dist/lib/run/host.js +46 -16
  34. package/dist/lib/run/tui.js +5 -2
  35. package/dist/lib/sandbox/agent-client-reconciler.js +4 -12
  36. package/dist/lib/sandbox/commands/create.js +3 -3
  37. package/dist/lib/sandbox/commands/enter.js +18 -4
  38. package/dist/lib/sandbox/config.js +3 -12
  39. package/dist/lib/sandbox/control/controller-registration.js +4 -2
  40. package/dist/lib/sandbox/control/executor.js +135 -40
  41. package/dist/lib/sandbox/control/lifecycle.js +29 -20
  42. package/dist/lib/sandbox/control/server.js +18 -16
  43. package/dist/lib/sandbox/mounts.js +3 -2
  44. package/dist/lib/sandbox/recovery.js +123 -22
  45. package/dist/lib/sandbox/workspace-identity.js +14 -0
  46. package/dist/lib/sandbox/workspace-view.js +8 -9
  47. package/dist/lib/self-update.js +278 -0
  48. package/dist/lib/server/protocol.js +5 -5
  49. package/dist/lib/task/activity-log.js +4 -1
  50. package/dist/lib/task/artifact-lifecycle.js +4 -2
  51. package/dist/lib/task/codex-orchestration.js +32 -35
  52. package/dist/lib/task/command-options.js +1 -3
  53. package/dist/lib/task/commands/cat.js +0 -5
  54. package/dist/lib/task/commands/decisions.js +76 -92
  55. package/dist/lib/task/commands/files.js +6 -6
  56. package/dist/lib/task/commands/grep.js +25 -61
  57. package/dist/lib/task/commands/issue-body.js +6 -6
  58. package/dist/lib/task/commands/log.js +25 -10
  59. package/dist/lib/task/commands/show.js +5 -6
  60. package/dist/lib/task/commands/status.js +8 -8
  61. package/dist/lib/task/commit-operation.js +21 -25
  62. package/dist/lib/task/commit-policy.js +1 -1
  63. package/dist/lib/task/control-authority.js +431 -0
  64. package/dist/lib/task/create.js +6 -1
  65. package/dist/lib/task/current-contract.js +35 -0
  66. package/dist/lib/task/decision-details.js +263 -0
  67. package/dist/lib/task/decision-intents.js +5 -2
  68. package/dist/lib/task/delegation-receipts.js +8 -7
  69. package/dist/lib/task/events.js +11 -5
  70. package/dist/lib/task/finalization.js +72 -46
  71. package/dist/lib/task/index.js +19 -29
  72. package/dist/lib/task/ledger-intents.js +8 -9
  73. package/dist/lib/task/ledger.js +13 -6
  74. package/dist/lib/task/lifecycle.js +16 -0
  75. package/dist/lib/task/orchestration.js +51 -14
  76. package/dist/lib/task/review-artifacts.js +31 -12
  77. package/dist/lib/task/review-finalization.js +19 -6
  78. package/dist/lib/task/verification-engine.js +38 -18
  79. package/dist/lib/task/verification-review.js +1 -1
  80. package/dist/lib/task/workspace-snapshot.js +5 -11
  81. package/dist/lib/task/write.js +11 -1
  82. package/dist/lib/update.js +6 -37
  83. package/dist/lib/version.js +5 -1
  84. package/dist/lifecycle-build-manifest.json +3 -3
  85. package/lib/agent-client.ts +0 -1
  86. package/lib/agent-clients/adapters/codex-lifecycle/build-identity.ts +25 -10
  87. package/lib/agent-clients/adapters/codex-lifecycle/controller-context.ts +16 -33
  88. package/lib/agent-clients/adapters/codex-lifecycle/sandbox-controller.ts +16 -35
  89. package/lib/agent-clients/adapters/codex-sandbox.ts +89 -14
  90. package/lib/agent-clients/adapters/index.ts +3 -1
  91. package/lib/agent-clients/adapters/opencode-sandbox.ts +0 -5
  92. package/lib/agent-clients/adapters/traecli.ts +66 -0
  93. package/lib/agent-clients/config.ts +14 -144
  94. package/lib/agent-clients/reconcile.ts +1 -12
  95. package/lib/agent-clients/schema.ts +5 -4
  96. package/lib/agent-clients/tokens.ts +7 -20
  97. package/lib/agent-clients/types.ts +2 -1
  98. package/lib/decide.ts +12 -22
  99. package/lib/defaults.json +9 -0
  100. package/lib/init.ts +2 -2
  101. package/lib/internal/codex-lifecycle.ts +2 -2
  102. package/lib/internal/codex-sandbox-controller.ts +4 -3
  103. package/lib/internal/release-workflow.ts +0 -1
  104. package/lib/internal/sandbox-control.ts +2 -2
  105. package/lib/internal/task-finalization.ts +27 -13
  106. package/lib/internal/task-ledger.ts +8 -2
  107. package/lib/internal/task-lifecycle.ts +33 -76
  108. package/lib/internal/task-orchestration.ts +33 -190
  109. package/lib/{task/commands/validate.ts → internal/task-validate.ts} +77 -41
  110. package/lib/merge.ts +236 -120
  111. package/lib/process-data/normalize.ts +2 -8
  112. package/lib/run/host.ts +63 -14
  113. package/lib/run/tui.ts +5 -3
  114. package/lib/sandbox/agent-client-reconciler.ts +5 -15
  115. package/lib/sandbox/commands/create.ts +4 -4
  116. package/lib/sandbox/commands/enter.ts +24 -4
  117. package/lib/sandbox/config.ts +2 -14
  118. package/lib/sandbox/control/container-identity.ts +2 -2
  119. package/lib/sandbox/control/controller-registration.ts +8 -3
  120. package/lib/sandbox/control/executor.ts +156 -53
  121. package/lib/sandbox/control/lifecycle.ts +34 -28
  122. package/lib/sandbox/control/protocol.ts +1 -3
  123. package/lib/sandbox/control/server.ts +15 -12
  124. package/lib/sandbox/control/state.ts +7 -7
  125. package/lib/sandbox/mounts.ts +4 -3
  126. package/lib/sandbox/recovery.ts +162 -34
  127. package/lib/sandbox/tools.ts +1 -1
  128. package/lib/sandbox/workspace-identity.ts +28 -0
  129. package/lib/sandbox/workspace-view.ts +14 -10
  130. package/lib/self-update.ts +341 -0
  131. package/lib/server/protocol.ts +5 -5
  132. package/lib/task/activity-log.ts +6 -1
  133. package/lib/task/artifact-lifecycle.ts +5 -3
  134. package/lib/task/codex-orchestration.ts +40 -45
  135. package/lib/task/command-options.ts +1 -2
  136. package/lib/task/commands/cat.ts +0 -4
  137. package/lib/task/commands/decisions.ts +80 -75
  138. package/lib/task/commands/files.ts +6 -6
  139. package/lib/task/commands/grep.ts +23 -51
  140. package/lib/task/commands/issue-body.ts +6 -6
  141. package/lib/task/commands/log.ts +22 -10
  142. package/lib/task/commands/show.ts +5 -6
  143. package/lib/task/commands/status.ts +8 -8
  144. package/lib/task/commit-operation.ts +25 -30
  145. package/lib/task/commit-policy.ts +1 -2
  146. package/lib/task/control-authority.ts +563 -0
  147. package/lib/task/create.ts +6 -1
  148. package/lib/task/current-contract.ts +49 -0
  149. package/lib/task/decision-details.ts +340 -0
  150. package/lib/task/decision-intents.ts +7 -2
  151. package/lib/task/delegation-receipts.ts +8 -6
  152. package/lib/task/events.ts +10 -5
  153. package/lib/task/finalization.ts +84 -42
  154. package/lib/task/index.ts +19 -28
  155. package/lib/task/ledger-intents.ts +6 -8
  156. package/lib/task/ledger.ts +17 -7
  157. package/lib/task/lifecycle.ts +20 -0
  158. package/lib/task/orchestration.ts +42 -16
  159. package/lib/task/review-artifacts.ts +53 -15
  160. package/lib/task/review-finalization.ts +33 -7
  161. package/lib/task/verification-engine.ts +33 -21
  162. package/lib/task/verification-review.ts +1 -1
  163. package/lib/task/workspace-snapshot.ts +4 -13
  164. package/lib/task/write.ts +20 -1
  165. package/lib/update.ts +6 -40
  166. package/lib/version.ts +6 -1
  167. package/package.json +1 -1
  168. package/templates/.agents/QUICKSTART.en.md +2 -3
  169. package/templates/.agents/QUICKSTART.zh-CN.md +2 -3
  170. package/templates/.agents/README.en.md +5 -3
  171. package/templates/.agents/README.zh-CN.md +5 -3
  172. package/templates/.agents/rules/README.en.md +1 -0
  173. package/templates/.agents/rules/README.zh-CN.md +1 -0
  174. package/templates/.agents/rules/compatibility-policy.en.md +40 -0
  175. package/templates/.agents/rules/compatibility-policy.zh-CN.md +40 -0
  176. package/templates/.agents/rules/create-issue.github.en.md +1 -1
  177. package/templates/.agents/rules/create-issue.github.zh-CN.md +1 -1
  178. package/templates/.agents/rules/human-decision-context.en.md +9 -7
  179. package/templates/.agents/rules/human-decision-context.zh-CN.md +9 -7
  180. package/templates/.agents/rules/issue-fields.github.en.md +1 -1
  181. package/templates/.agents/rules/issue-fields.github.zh-CN.md +1 -1
  182. package/templates/.agents/rules/issue-pr-commands.en.md +1 -1
  183. package/templates/.agents/rules/issue-pr-commands.github.en.md +1 -1
  184. package/templates/.agents/rules/issue-pr-commands.github.zh-CN.md +1 -1
  185. package/templates/.agents/rules/issue-pr-commands.zh-CN.md +1 -1
  186. package/templates/.agents/rules/issue-sync.github.en.md +1 -1
  187. package/templates/.agents/rules/issue-sync.github.zh-CN.md +2 -2
  188. package/templates/.agents/rules/lifecycle-orchestration.en.md +4 -4
  189. package/templates/.agents/rules/lifecycle-orchestration.zh-CN.md +4 -4
  190. package/templates/.agents/rules/milestone-inference.github.en.md +1 -1
  191. package/templates/.agents/rules/milestone-inference.github.zh-CN.md +1 -1
  192. package/templates/.agents/rules/next-step-output.en.md +3 -3
  193. package/templates/.agents/rules/next-step-output.zh-CN.md +3 -3
  194. package/templates/.agents/rules/no-mid-flow-questions.en.md +1 -1
  195. package/templates/.agents/rules/no-mid-flow-questions.zh-CN.md +1 -1
  196. package/templates/.agents/rules/pr-sync.en.md +2 -2
  197. package/templates/.agents/rules/pr-sync.github.en.md +3 -2
  198. package/templates/.agents/rules/pr-sync.github.zh-CN.md +3 -1
  199. package/templates/.agents/rules/pr-sync.zh-CN.md +2 -1
  200. package/templates/.agents/rules/release-commands.github.en.md +6 -0
  201. package/templates/.agents/rules/release-commands.github.zh-CN.md +6 -0
  202. package/templates/.agents/rules/review-handshake.en.md +1 -1
  203. package/templates/.agents/rules/review-handshake.zh-CN.md +1 -1
  204. package/templates/.agents/rules/review-method.en.md +1 -0
  205. package/templates/.agents/rules/review-method.zh-CN.md +1 -0
  206. package/templates/.agents/rules/task-management.en.md +1 -2
  207. package/templates/.agents/rules/task-management.zh-CN.md +1 -2
  208. package/templates/.agents/skills/analyze-task/SKILL.en.md +4 -3
  209. package/templates/.agents/skills/analyze-task/SKILL.zh-CN.md +4 -3
  210. package/templates/.agents/skills/block-task/SKILL.en.md +2 -2
  211. package/templates/.agents/skills/block-task/SKILL.zh-CN.md +2 -2
  212. package/templates/.agents/skills/cancel-task/SKILL.en.md +2 -2
  213. package/templates/.agents/skills/cancel-task/SKILL.zh-CN.md +2 -2
  214. package/templates/.agents/skills/check-task/SKILL.en.md +2 -2
  215. package/templates/.agents/skills/check-task/SKILL.zh-CN.md +2 -2
  216. package/templates/.agents/skills/close-codescan/SKILL.en.md +1 -1
  217. package/templates/.agents/skills/close-codescan/SKILL.zh-CN.md +1 -1
  218. package/templates/.agents/skills/close-dependabot/SKILL.en.md +1 -1
  219. package/templates/.agents/skills/close-dependabot/SKILL.zh-CN.md +1 -1
  220. package/templates/.agents/skills/code-task/SKILL.en.md +4 -3
  221. package/templates/.agents/skills/code-task/SKILL.zh-CN.md +5 -3
  222. package/templates/.agents/skills/commit/SKILL.en.md +27 -7
  223. package/templates/.agents/skills/commit/SKILL.zh-CN.md +3 -4
  224. package/templates/.agents/skills/complete-manual-validation/SKILL.en.md +5 -5
  225. package/templates/.agents/skills/complete-manual-validation/SKILL.zh-CN.md +5 -5
  226. package/templates/.agents/skills/complete-task/SKILL.en.md +3 -3
  227. package/templates/.agents/skills/complete-task/SKILL.zh-CN.md +3 -3
  228. package/templates/.agents/skills/create-pr/SKILL.en.md +15 -11
  229. package/templates/.agents/skills/create-pr/SKILL.zh-CN.md +15 -11
  230. package/templates/.agents/skills/create-pr/reference/change-report.en.md +46 -0
  231. package/templates/.agents/skills/create-pr/reference/change-report.zh-CN.md +46 -0
  232. package/templates/.agents/skills/create-pr/scripts/change-report.mjs +203 -0
  233. package/templates/.agents/skills/create-release-note/SKILL.en.md +5 -6
  234. package/templates/.agents/skills/create-release-note/SKILL.zh-CN.md +5 -6
  235. package/templates/.agents/skills/create-task/SKILL.en.md +1 -1
  236. package/templates/.agents/skills/create-task/SKILL.zh-CN.md +1 -1
  237. package/templates/.agents/skills/import-issue/SKILL.en.md +1 -1
  238. package/templates/.agents/skills/import-issue/SKILL.zh-CN.md +1 -1
  239. package/templates/.agents/skills/plan-task/SKILL.en.md +5 -4
  240. package/templates/.agents/skills/plan-task/SKILL.zh-CN.md +5 -4
  241. package/templates/.agents/skills/restore-task/SKILL.en.md +1 -1
  242. package/templates/.agents/skills/restore-task/SKILL.zh-CN.md +1 -1
  243. package/templates/.agents/skills/review-analysis/SKILL.en.md +5 -3
  244. package/templates/.agents/skills/review-analysis/SKILL.zh-CN.md +5 -3
  245. package/templates/.agents/skills/review-analysis/config/verify.en.json +1 -0
  246. package/templates/.agents/skills/review-analysis/config/verify.zh-CN.json +1 -0
  247. package/templates/.agents/skills/review-code/SKILL.en.md +5 -3
  248. package/templates/.agents/skills/review-code/SKILL.zh-CN.md +5 -3
  249. package/templates/.agents/skills/review-code/config/verify.en.json +1 -0
  250. package/templates/.agents/skills/review-code/config/verify.zh-CN.json +1 -0
  251. package/templates/.agents/skills/review-code/reference/migration-risks.en.md +9 -6
  252. package/templates/.agents/skills/review-code/reference/migration-risks.zh-CN.md +9 -6
  253. package/templates/.agents/skills/review-plan/SKILL.en.md +5 -3
  254. package/templates/.agents/skills/review-plan/SKILL.zh-CN.md +5 -3
  255. package/templates/.agents/skills/review-plan/config/verify.en.json +1 -0
  256. package/templates/.agents/skills/review-plan/config/verify.zh-CN.json +1 -0
  257. package/templates/.agents/skills/run-manual-validation/SKILL.en.md +7 -3
  258. package/templates/.agents/skills/run-manual-validation/SKILL.zh-CN.md +7 -3
  259. package/templates/.agents/skills/run-manual-validation/reference/discovery-and-execution.en.md +1 -1
  260. package/templates/.agents/skills/run-manual-validation/reference/discovery-and-execution.zh-CN.md +1 -1
  261. package/templates/.agents/skills/run-manual-validation/reference/report-template.en.md +2 -2
  262. package/templates/.agents/skills/run-manual-validation/reference/report-template.zh-CN.md +2 -2
  263. package/templates/.agents/skills/run-task/SKILL.en.md +6 -2
  264. package/templates/.agents/skills/run-task/SKILL.zh-CN.md +6 -2
  265. package/templates/.agents/skills/run-task/reference/host-validation.en.md +2 -2
  266. package/templates/.agents/skills/run-task/reference/host-validation.zh-CN.md +2 -2
  267. package/templates/.agents/skills/update-agent-infra/SKILL.en.md +2 -2
  268. package/templates/.agents/skills/update-agent-infra/SKILL.zh-CN.md +2 -2
  269. package/templates/.agents/skills/update-agent-infra/scripts/sync-templates.js +159 -104
  270. package/templates/.agents/skills/watch-pr/SKILL.en.md +2 -2
  271. package/templates/.agents/skills/watch-pr/SKILL.zh-CN.md +2 -2
  272. package/templates/.agents/templates/task.en.md +1 -1
  273. package/templates/.agents/templates/task.zh-CN.md +1 -1
  274. package/templates/.claude/commands/analyze-task.en.md +1 -1
  275. package/templates/.claude/commands/analyze-task.zh-CN.md +1 -1
  276. package/templates/.claude/commands/block-task.en.md +1 -1
  277. package/templates/.claude/commands/block-task.zh-CN.md +1 -1
  278. package/templates/.claude/commands/cancel-task.en.md +1 -1
  279. package/templates/.claude/commands/cancel-task.zh-CN.md +1 -1
  280. package/templates/.claude/commands/check-task.en.md +1 -1
  281. package/templates/.claude/commands/check-task.zh-CN.md +1 -1
  282. package/templates/.claude/commands/code-task.en.md +1 -1
  283. package/templates/.claude/commands/code-task.zh-CN.md +1 -1
  284. package/templates/.claude/commands/commit.en.md +1 -1
  285. package/templates/.claude/commands/commit.zh-CN.md +1 -1
  286. package/templates/.claude/commands/complete-manual-validation.en.md +1 -1
  287. package/templates/.claude/commands/complete-manual-validation.zh-CN.md +1 -1
  288. package/templates/.claude/commands/complete-task.en.md +1 -1
  289. package/templates/.claude/commands/complete-task.zh-CN.md +1 -1
  290. package/templates/.claude/commands/create-pr.en.md +1 -1
  291. package/templates/.claude/commands/create-pr.zh-CN.md +1 -1
  292. package/templates/.claude/commands/plan-task.en.md +1 -1
  293. package/templates/.claude/commands/plan-task.zh-CN.md +1 -1
  294. package/templates/.claude/commands/review-analysis.en.md +1 -1
  295. package/templates/.claude/commands/review-analysis.zh-CN.md +1 -1
  296. package/templates/.claude/commands/review-code.en.md +1 -1
  297. package/templates/.claude/commands/review-code.zh-CN.md +1 -1
  298. package/templates/.claude/commands/review-plan.en.md +1 -1
  299. package/templates/.claude/commands/review-plan.zh-CN.md +1 -1
  300. package/templates/.claude/commands/run-manual-validation.en.md +1 -1
  301. package/templates/.claude/commands/run-manual-validation.zh-CN.md +1 -1
  302. package/templates/.claude/commands/run-task.en.md +1 -1
  303. package/templates/.claude/commands/run-task.zh-CN.md +1 -1
  304. package/templates/.claude/commands/watch-pr.en.md +1 -1
  305. package/templates/.claude/commands/watch-pr.zh-CN.md +1 -1
  306. package/templates/.traecli/commands/update-agent-infra.en.md +7 -0
  307. package/templates/.traecli/commands/update-agent-infra.zh-CN.md +7 -0
  308. package/dist/lib/builtin-tuis.js +0 -40
  309. package/lib/builtin-tuis.ts +0 -56
@@ -8,5 +8,9 @@ if (!packageJsonUrl) {
8
8
  }
9
9
  const { version } = JSON.parse(readFileSync(packageJsonUrl, 'utf8'));
10
10
  const VERSION = `v${version}`;
11
- export { VERSION };
11
+ const AGENT_INFRA_VERSION_PATTERN = /^v\d+\.\d+\.\d+(?:-[0-9A-Za-z.-]+)?(?:\+[0-9A-Za-z.-]+)?$/;
12
+ function isValidAgentInfraVersion(value) {
13
+ return typeof value === 'string' && AGENT_INFRA_VERSION_PATTERN.test(value);
14
+ }
15
+ export { VERSION, isValidAgentInfraVersion };
12
16
  //# sourceMappingURL=version.js.map
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "protocolVersion": 3,
3
- "packageVersion": "0.9.9",
4
- "sourceInputHash": "2f2db695db557531b3139eccd1bd530fbeb7b99409e2d49338f3b4646aac9ef6",
5
- "internalExecutableBuildHash": "1391ebe2614f3071e7a60920325046a47f1473e7fb23c821327072f947f639d3"
3
+ "packageVersion": "0.9.11",
4
+ "sourceInputHash": "00e07caf1313615df10d46ae620767d7d15c3cc59712c1da581623057b87e0a6",
5
+ "internalExecutableBuildHash": "8a481b1d79da5e5f31ef79cd3428f1b51df2b859e70724e50dcc5910f8ee40c6"
6
6
  }
@@ -128,7 +128,6 @@ async function cmdAgentClient(args: string[]): Promise<number> {
128
128
  throw new AgentClientCommandError('AGENT_CLIENT_ARGUMENT_INVALID', 'status accepts no arguments');
129
129
  }
130
130
  const plan = workflowPlan(projectRoot, config, { type: 'none' });
131
- process.stdout.write(`source: ${plan.source}\n`);
132
131
  printState(plan.desired);
133
132
  for (const seed of plan.seedOperations) {
134
133
  process.stdout.write(` seed ${seed.target}: ${seed.kind}\n`);
@@ -28,6 +28,13 @@ type IdentityVerification = Readonly<{
28
28
  ok: boolean;
29
29
  code: string | null;
30
30
  message: string | null;
31
+ warnings: readonly LifecycleIdentityWarning[];
32
+ }>;
33
+
34
+ type LifecycleIdentityWarning = Readonly<{
35
+ code: 'CODEX_LIFECYCLE_BUILD_MISMATCH' | 'CODEX_LIFECYCLE_CONTRACT_MISMATCH';
36
+ message: string;
37
+ action: 'rebuild-sandbox';
31
38
  }>;
32
39
 
33
40
  function exactText(value: unknown): value is string {
@@ -201,25 +208,32 @@ function verifyLifecycleBuildIdentity(
201
208
  return {
202
209
  ok: false,
203
210
  code: 'CODEX_LIFECYCLE_PROTOCOL_MISMATCH',
204
- message: 'Codex lifecycle protocol version does not match'
211
+ message: 'Codex lifecycle protocol version does not match',
212
+ warnings: []
205
213
  };
206
214
  }
215
+ const warnings: LifecycleIdentityWarning[] = [];
207
216
  if (actual.packageVersion !== expected.packageVersion
208
217
  || actual.internalExecutableBuildHash !== expected.internalExecutableBuildHash) {
209
- return {
210
- ok: false,
218
+ warnings.push({
211
219
  code: 'CODEX_LIFECYCLE_BUILD_MISMATCH',
212
- message: 'Codex lifecycle executable build identity does not match'
213
- };
220
+ message: 'Codex lifecycle executable build identity differs; rebuild the sandbox if the runtime is stale',
221
+ action: 'rebuild-sandbox'
222
+ });
214
223
  }
215
224
  if (actual.lifecycleContractHash !== expected.lifecycleContractHash) {
216
- return {
217
- ok: false,
225
+ warnings.push({
218
226
  code: 'CODEX_LIFECYCLE_CONTRACT_MISMATCH',
219
- message: 'Codex lifecycle contract identity does not match'
220
- };
227
+ message: 'Codex lifecycle contract identity differs; rebuild the sandbox if the runtime is stale',
228
+ action: 'rebuild-sandbox'
229
+ });
221
230
  }
222
- return { ok: true, code: null, message: null };
231
+ return {
232
+ ok: true,
233
+ code: null,
234
+ message: null,
235
+ warnings: Object.freeze(warnings)
236
+ };
223
237
  }
224
238
 
225
239
  export {
@@ -233,6 +247,7 @@ export {
233
247
  };
234
248
  export type {
235
249
  IdentityVerification,
250
+ LifecycleIdentityWarning,
236
251
  LifecycleBuildIdentity,
237
252
  LifecycleManifestFiles,
238
253
  LifecycleBuildIdentityOptions
@@ -4,7 +4,12 @@ import path from 'node:path';
4
4
 
5
5
  import { getProcessIdentityState, type ProcessIdentity } from '../../../server/process-state.ts';
6
6
  import type { CodexControllerLeaseProofV1, CodexControllerLeaseV1 } from '../../../sandbox/control/controller-registration.ts';
7
- import { computeLifecycleBuildIdentity, type LifecycleBuildIdentity } from './build-identity.ts';
7
+ import {
8
+ computeLifecycleBuildIdentity,
9
+ verifyLifecycleBuildIdentity,
10
+ type LifecycleBuildIdentity,
11
+ type LifecycleIdentityWarning
12
+ } from './build-identity.ts';
8
13
 
9
14
  const HEX_256 = /^[a-f0-9]{64}$/u;
10
15
 
@@ -19,30 +24,12 @@ export type CodexSandboxControllerContextV2 = Readonly<{
19
24
  expiresAt: number;
20
25
  buildIdentity: LifecycleBuildIdentity;
21
26
  hookDefinitionHash: string;
22
- lifecycleProfilesHash: string;
23
27
  }>;
24
28
 
25
29
  function exactKeys(value: Record<string, unknown>, keys: readonly string[]): boolean {
26
30
  return Object.keys(value).sort().join(',') === [...keys].sort().join(',');
27
31
  }
28
32
 
29
- function digestProfiles(repoRoot: string): string {
30
- const files = [
31
- path.join(repoRoot, '.codex', 'agents', 'agent-infra-lifecycle-executor.toml'),
32
- path.join(repoRoot, '.codex', 'agents', 'agent-infra-lifecycle-reviewer.toml')
33
- ];
34
- const hash = crypto.createHash('sha256');
35
- for (const file of files.sort()) {
36
- const stat = fs.lstatSync(file);
37
- if (!stat.isFile() || stat.isSymbolicLink()) throw new Error('CODEX_SANDBOX_CONTROLLER_BUNDLE_MISMATCH');
38
- hash.update(path.basename(file));
39
- hash.update('\0');
40
- hash.update(fs.readFileSync(file));
41
- hash.update('\0');
42
- }
43
- return hash.digest('hex');
44
- }
45
-
46
33
  function validProcess(value: unknown): value is ProcessIdentity {
47
34
  if (!value || typeof value !== 'object' || Array.isArray(value)) return false;
48
35
  const identity = value as Record<string, unknown>;
@@ -72,7 +59,7 @@ function validateContext(value: unknown): CodexSandboxControllerContextV2 {
72
59
  if (!exactKeys(context, [
73
60
  'buildIdentity', 'controlGeneration', 'controllerInstanceDigest', 'controllerLease',
74
61
  'controllerProcess', 'expiresAt', 'hookDefinitionHash', 'issuedAt',
75
- 'lifecycleProfilesHash', 'taskId', 'version'
62
+ 'taskId', 'version'
76
63
  ])
77
64
  || context.version !== 2
78
65
  || typeof context.taskId !== 'string' || context.taskId.length === 0
@@ -87,8 +74,7 @@ function validateContext(value: unknown): CodexSandboxControllerContextV2 {
87
74
  || !Number.isSafeInteger(context.expiresAt)
88
75
  || (context.expiresAt as number) <= (context.issuedAt as number)
89
76
  || !validBuildIdentity(context.buildIdentity)
90
- || typeof context.hookDefinitionHash !== 'string' || !HEX_256.test(context.hookDefinitionHash)
91
- || typeof context.lifecycleProfilesHash !== 'string' || !HEX_256.test(context.lifecycleProfilesHash)) {
77
+ || typeof context.hookDefinitionHash !== 'string' || !HEX_256.test(context.hookDefinitionHash)) {
92
78
  throw new Error('CODEX_SANDBOX_CONTROLLER_CONTEXT_INVALID');
93
79
  }
94
80
  return context as unknown as CodexSandboxControllerContextV2;
@@ -96,7 +82,7 @@ function validateContext(value: unknown): CodexSandboxControllerContextV2 {
96
82
 
97
83
  export function contextFromControllerLease(
98
84
  lease: CodexControllerLeaseV1,
99
- hashes: Readonly<{ hookDefinitionHash: string; lifecycleProfilesHash: string }>
85
+ input: Readonly<{ hookDefinitionHash: string }>
100
86
  ): CodexSandboxControllerContextV2 {
101
87
  return Object.freeze({
102
88
  version: 2,
@@ -108,8 +94,7 @@ export function contextFromControllerLease(
108
94
  issuedAt: lease.issuedAt,
109
95
  expiresAt: lease.expiresAt,
110
96
  buildIdentity: lease.buildIdentity,
111
- hookDefinitionHash: hashes.hookDefinitionHash,
112
- lifecycleProfilesHash: hashes.lifecycleProfilesHash
97
+ hookDefinitionHash: input.hookDefinitionHash
113
98
  });
114
99
  }
115
100
 
@@ -129,7 +114,7 @@ export function writeCodexSandboxControllerContext(
129
114
  }
130
115
  }
131
116
 
132
- export function verifyCodexSandboxControllerContext(
117
+ export function verifyCodexSandboxControllerContextWithWarnings(
133
118
  contextPath: string,
134
119
  options: Readonly<{
135
120
  repoRoot?: string;
@@ -137,7 +122,7 @@ export function verifyCodexSandboxControllerContext(
137
122
  generation?: string;
138
123
  probeProcess?: (identity: ProcessIdentity) => 'alive' | 'dead' | 'unknown';
139
124
  }> = {}
140
- ): CodexSandboxControllerContextV2 {
125
+ ): Readonly<{ context: CodexSandboxControllerContextV2; warnings: readonly LifecycleIdentityWarning[] }> {
141
126
  let stat: fs.Stats;
142
127
  try {
143
128
  stat = fs.lstatSync(contextPath);
@@ -162,12 +147,10 @@ export function verifyCodexSandboxControllerContext(
162
147
  || state !== 'alive') {
163
148
  throw new Error('CODEX_SANDBOX_CONTROLLER_CONTEXT_INVALID');
164
149
  }
165
- if (JSON.stringify(computeLifecycleBuildIdentity(repoRoot)) !== JSON.stringify(context.buildIdentity)
166
- || crypto.createHash('sha256').update(fs.readFileSync(path.join(repoRoot, '.codex', 'hooks.json'))).digest('hex') !== context.hookDefinitionHash
167
- || digestProfiles(repoRoot) !== context.lifecycleProfilesHash) {
168
- throw new Error('CODEX_SANDBOX_CONTROLLER_BUNDLE_MISMATCH');
169
- }
170
- return Object.freeze(context);
150
+ const currentBuildIdentity = computeLifecycleBuildIdentity(repoRoot);
151
+ const identity = verifyLifecycleBuildIdentity(context.buildIdentity, currentBuildIdentity);
152
+ if (!identity.ok) throw new Error(`${identity.code}: ${identity.message}`);
153
+ return Object.freeze({ context: Object.freeze(context), warnings: identity.warnings });
171
154
  }
172
155
 
173
156
  export function controllerProofFromContext(context: CodexSandboxControllerContextV2): CodexControllerLeaseProofV1 {
@@ -14,11 +14,11 @@ import {
14
14
  } from '../../../sandbox/control/client.ts';
15
15
  import { readSandboxControlStatus } from '../../../sandbox/control/state.ts';
16
16
  import { getProcessStartTime, type ProcessIdentity } from '../../../server/process-state.ts';
17
- import { computeLifecycleBuildIdentity } from './build-identity.ts';
17
+ import { LIFECYCLE_PROTOCOL_VERSION, type LifecycleIdentityWarning } from './build-identity.ts';
18
18
  import {
19
19
  contextFromControllerLease,
20
20
  controllerProofFromContext,
21
- verifyCodexSandboxControllerContext as verifyContextFile,
21
+ verifyCodexSandboxControllerContextWithWarnings as verifyContextFileWithWarnings,
22
22
  writeCodexSandboxControllerContext,
23
23
  type CodexSandboxControllerContextV2
24
24
  } from './controller-context.ts';
@@ -70,21 +70,6 @@ type VerifyContextOptions = Readonly<{
70
70
  requestControllerVerify?: typeof requestCodexControllerVerify;
71
71
  }>;
72
72
 
73
- function digestFiles(files: readonly string[]): string {
74
- const hash = crypto.createHash('sha256');
75
- for (const file of [...files].sort()) {
76
- const stat = fs.lstatSync(file);
77
- if (!stat.isFile() || stat.isSymbolicLink()) {
78
- throw new Error('CODEX_SANDBOX_CONTROLLER_BUNDLE_MISMATCH');
79
- }
80
- hash.update(path.basename(file));
81
- hash.update('\0');
82
- hash.update(fs.readFileSync(file));
83
- hash.update('\0');
84
- }
85
- return hash.digest('hex');
86
- }
87
-
88
73
  function copyRegular(source: string, destination: string, mode: number): void {
89
74
  const stat = fs.lstatSync(source);
90
75
  if (!stat.isFile() || stat.isSymbolicLink()) {
@@ -166,17 +151,18 @@ function verifyControl(taskId: string, control: ControllerControl): void {
166
151
  if (payload.taskId !== taskId) throw new Error('CODEX_SANDBOX_CONTROLLER_TASK_BINDING_INVALID');
167
152
  }
168
153
 
169
- function verifyCodexSandboxControllerContext(
154
+ function verifyCodexSandboxControllerContextWithWarnings(
170
155
  contextPath: string,
171
156
  options: VerifyContextOptions = {}
172
- ): CodexSandboxControllerContextV2 {
157
+ ): Readonly<{ context: CodexSandboxControllerContextV2; warnings: readonly LifecycleIdentityWarning[] }> {
173
158
  const control = options.control ?? controlFromEnvironment();
174
- const context = verifyContextFile(contextPath, {
159
+ const fileVerification = verifyContextFileWithWarnings(contextPath, {
175
160
  repoRoot: options.repoRoot,
176
161
  now: options.now,
177
162
  generation: control.generation,
178
163
  probeProcess: options.probeProcess
179
164
  });
165
+ const context = fileVerification.context;
180
166
  const verified = (options.requestControllerVerify ?? requestCodexControllerVerify)({
181
167
  controllerProof: controllerProofFromContext(context),
182
168
  ...control,
@@ -187,7 +173,10 @@ function verifyCodexSandboxControllerContext(
187
173
  || verified.binding.controllerInstanceDigest !== context.controllerInstanceDigest) {
188
174
  throw new Error('CODEX_SANDBOX_CONTROLLER_CONTEXT_INVALID');
189
175
  }
190
- return context;
176
+ return Object.freeze({
177
+ context,
178
+ warnings: fileVerification.warnings
179
+ });
191
180
  }
192
181
 
193
182
  function detectedCodexVersion(): string {
@@ -337,30 +326,22 @@ function prepareCodexSandboxController(
337
326
  copyRegular(hooks, path.join(home, 'hooks.json'), 0o600);
338
327
  copyRegular(executor, path.join(home, 'agents', path.basename(executor)), 0o600);
339
328
  copyRegular(reviewer, path.join(home, 'agents', path.basename(reviewer)), 0o600);
340
- if (crypto.createHash('sha256').update(fs.readFileSync(path.join(home, 'hooks.json'))).digest('hex')
341
- !== crypto.createHash('sha256').update(fs.readFileSync(hooks)).digest('hex')
342
- || digestFiles([
343
- path.join(home, 'agents', path.basename(executor)),
344
- path.join(home, 'agents', path.basename(reviewer))
345
- ]) !== digestFiles([executor, reviewer])) {
346
- throw new Error('CODEX_SANDBOX_CONTROLLER_BUNDLE_MISMATCH');
347
- }
348
329
 
349
- const buildIdentity = computeLifecycleBuildIdentity(repoRoot);
350
330
  const opened = (options.openController ?? requestCodexControllerOpen)({
351
331
  controllerProcess: { pid: process.pid, startTime: parentStartTime },
352
332
  ...control,
353
333
  timeoutMs: 30_000
354
334
  });
355
335
  const taskId = opened.lease.taskId;
336
+ if (opened.lease.buildIdentity.protocolVersion !== LIFECYCLE_PROTOCOL_VERSION) {
337
+ throw new Error('CODEX_LIFECYCLE_PROTOCOL_MISMATCH: Codex lifecycle protocol version does not match');
338
+ }
356
339
  context = contextFromControllerLease(opened.lease, {
357
- hookDefinitionHash: crypto.createHash('sha256').update(fs.readFileSync(hooks)).digest('hex'),
358
- lifecycleProfilesHash: digestFiles([executor, reviewer])
340
+ hookDefinitionHash: crypto.createHash('sha256').update(fs.readFileSync(hooks)).digest('hex')
359
341
  });
360
342
  if (opened.lease.controlGeneration !== control.generation
361
343
  || opened.lease.controllerProcess.pid !== process.pid
362
- || opened.lease.controllerProcess.startTime !== parentStartTime
363
- || JSON.stringify(opened.lease.buildIdentity) !== JSON.stringify(buildIdentity)) {
344
+ || opened.lease.controllerProcess.startTime !== parentStartTime) {
364
345
  throw new Error('SANDBOX_CONTROL_RESULT_INVALID');
365
346
  }
366
347
  (options.verifyTaskBinding ?? verifyControl)(taskId, control);
@@ -460,7 +441,7 @@ async function runCodexSandboxController(
460
441
  export {
461
442
  prepareCodexSandboxController,
462
443
  runCodexSandboxController,
463
- verifyCodexSandboxControllerContext,
444
+ verifyCodexSandboxControllerContextWithWarnings,
464
445
  controllerProofFromContext
465
446
  };
466
447
  export type {
@@ -37,6 +37,8 @@ function resolveHostCatalogPath(value: unknown, hostHomeDir: string): string | n
37
37
  }
38
38
 
39
39
  const CODEX_DISABLED_FEATURE_FLAGS = ['apps', 'enable_mcp_apps'] as const;
40
+ const SANDBOX_CODEX_HOOKS_PATH = '/workspace/.codex/hooks.json';
41
+ const CODEX_HOOK_TRUST_HASH = /^sha256:[a-f0-9]{64}$/;
40
42
 
41
43
  function removeCodexMcpServers(sandboxParsed: JsonObject): boolean {
42
44
  if (!Object.hasOwn(sandboxParsed, 'mcp_servers')) {
@@ -75,27 +77,75 @@ function inheritDisabledCodexFeatureFlags(
75
77
  return changed;
76
78
  }
77
79
 
80
+ function inheritCodexHookTrustState(
81
+ sandboxParsed: JsonObject,
82
+ hostParsed: JsonObject,
83
+ hostProjectDir?: string
84
+ ): boolean {
85
+ if (!hostProjectDir) {
86
+ return false;
87
+ }
88
+
89
+ if (Object.hasOwn(sandboxParsed, 'hooks') && !isJsonObjectRecord(sandboxParsed.hooks)) {
90
+ return false;
91
+ }
92
+ const sandboxHooks = (sandboxParsed.hooks as JsonObject | undefined) ?? {};
93
+ if (Object.hasOwn(sandboxHooks, 'state') && !isJsonObjectRecord(sandboxHooks.state)) {
94
+ return false;
95
+ }
96
+
97
+ const sandboxState = (sandboxHooks.state as JsonObject | undefined) ?? {};
98
+ const sandboxPrefix = `${SANDBOX_CODEX_HOOKS_PATH}:`;
99
+ const nextState = Object.fromEntries(
100
+ Object.entries(sandboxState).filter(([key]) => !key.startsWith(sandboxPrefix))
101
+ );
102
+
103
+ const hostState = isJsonObjectRecord(hostParsed.hooks)
104
+ && isJsonObjectRecord(hostParsed.hooks.state)
105
+ ? hostParsed.hooks.state
106
+ : {};
107
+ const hostPrefix = `${path.join(hostProjectDir, '.codex', 'hooks.json')}:`;
108
+ for (const [key, value] of Object.entries(hostState)) {
109
+ if (!key.startsWith(hostPrefix) || !isJsonObjectRecord(value)) {
110
+ continue;
111
+ }
112
+ const trustedHash = value.trusted_hash;
113
+ if (typeof trustedHash !== 'string' || !CODEX_HOOK_TRUST_HASH.test(trustedHash)) {
114
+ continue;
115
+ }
116
+ nextState[`${sandboxPrefix}${key.slice(hostPrefix.length)}`] = {
117
+ trusted_hash: trustedHash,
118
+ ...(typeof value.enabled === 'boolean' ? { enabled: value.enabled } : {})
119
+ };
120
+ }
121
+
122
+ if (JSON.stringify(sandboxState) === JSON.stringify(nextState)) {
123
+ return false;
124
+ }
125
+ if (Object.keys(nextState).length > 0) {
126
+ sandboxHooks.state = nextState;
127
+ sandboxParsed.hooks = sandboxHooks;
128
+ } else {
129
+ delete sandboxHooks.state;
130
+ if (Object.keys(sandboxHooks).length > 0) {
131
+ sandboxParsed.hooks = sandboxHooks;
132
+ } else {
133
+ delete sandboxParsed.hooks;
134
+ }
135
+ }
136
+ return true;
137
+ }
138
+
78
139
  function ensureCodexModelInheritance(
79
140
  toolDir: string,
80
141
  hostHomeDir?: string,
81
- containerCodexDir: string = '/home/devuser/.codex'
142
+ containerCodexDir: string = '/home/devuser/.codex',
143
+ hostProjectDir?: string
82
144
  ): void {
83
145
  if (!hostHomeDir) {
84
146
  return;
85
147
  }
86
148
 
87
- const hostConfigPath = path.join(hostHomeDir, '.codex', 'config.toml');
88
- if (!fs.existsSync(hostConfigPath)) {
89
- return;
90
- }
91
-
92
- let hostParsed: JsonObject;
93
- try {
94
- hostParsed = toml.parse(fs.readFileSync(hostConfigPath, 'utf8')) as JsonObject;
95
- } catch {
96
- return;
97
- }
98
-
99
149
  const sandboxConfigPath = path.join(toolDir, 'config.toml');
100
150
  // This rewrites sandbox-side TOML and drops comments; the host config stays untouched.
101
151
  let sandboxParsed: JsonObject = {};
@@ -107,8 +157,25 @@ function ensureCodexModelInheritance(
107
157
  }
108
158
  }
109
159
 
160
+ const hostConfigPath = path.join(hostHomeDir, '.codex', 'config.toml');
161
+ let hostParsed: JsonObject | null = null;
162
+ if (fs.existsSync(hostConfigPath)) {
163
+ try {
164
+ hostParsed = toml.parse(fs.readFileSync(hostConfigPath, 'utf8')) as JsonObject;
165
+ } catch {
166
+ // An unavailable host trust source must not leave previously projected trust active.
167
+ }
168
+ }
169
+ if (!hostParsed) {
170
+ if (inheritCodexHookTrustState(sandboxParsed, {}, hostProjectDir)) {
171
+ fs.writeFileSync(sandboxConfigPath, `${toml.stringify(sandboxParsed)}\n`, 'utf8');
172
+ }
173
+ return;
174
+ }
175
+
110
176
  let changed = removeCodexMcpServers(sandboxParsed);
111
177
  changed = inheritDisabledCodexFeatureFlags(sandboxParsed, hostParsed) || changed;
178
+ changed = inheritCodexHookTrustState(sandboxParsed, hostParsed, hostProjectDir) || changed;
112
179
 
113
180
  const inheritSpecs: Array<readonly [string, 'string' | 'number']> = [
114
181
  ['model', 'string'],
@@ -180,7 +247,15 @@ const codexBeforeContainerCreateHook: AgentClientSandboxHook = {
180
247
  message: 'Codex sandbox hook requires its resolved tool state.'
181
248
  };
182
249
  }
183
- ensureCodexModelInheritance(entry.dir, create.hostHome, entry.tool.containerMount);
250
+ const hostProjectDir = typeof context.config?.repoRoot === 'string'
251
+ ? context.config.repoRoot
252
+ : undefined;
253
+ ensureCodexModelInheritance(
254
+ entry.dir,
255
+ create.hostHome,
256
+ entry.tool.containerMount,
257
+ hostProjectDir
258
+ );
184
259
  ensureCodexWorkspaceTrust(entry.dir);
185
260
  return { status: 'ready' };
186
261
  }
@@ -4,13 +4,15 @@ import { claudeCodeAdapter } from './claude-code.ts';
4
4
  import { codexAdapter } from './codex.ts';
5
5
  import { antigravityCliAdapter } from './antigravity-cli.ts';
6
6
  import { opencodeAdapter } from './opencode.ts';
7
+ import { traecliAdapter } from './traecli.ts';
7
8
 
8
9
  const adaptersById = new Map(
9
10
  [
10
11
  claudeCodeAdapter,
11
12
  codexAdapter,
12
13
  antigravityCliAdapter,
13
- opencodeAdapter
14
+ opencodeAdapter,
15
+ traecliAdapter
14
16
  ].map((adapter) => [adapter.id, adapter])
15
17
  );
16
18
 
@@ -33,14 +33,9 @@ function ensureOpenCodeSandboxState(
33
33
  const canonicalConfigDir = path.join(toolDir, '.xdg', 'config', 'opencode');
34
34
  const canonicalStateDir = path.join(toolDir, '.xdg', 'state', 'opencode');
35
35
  const canonicalConfigPath = path.join(canonicalConfigDir, 'opencode.json');
36
- const legacyConfigPath = path.join(toolDir, 'opencode.json');
37
36
  fs.mkdirSync(canonicalConfigDir, { recursive: true });
38
37
  fs.mkdirSync(canonicalStateDir, { recursive: true });
39
38
 
40
- if (!fs.existsSync(canonicalConfigPath) && fs.existsSync(legacyConfigPath)) {
41
- fs.copyFileSync(legacyConfigPath, canonicalConfigPath, fs.constants.COPYFILE_EXCL);
42
- }
43
-
44
39
  const hostConfigRoot = resolveXdgRoot(
45
40
  hostEnv.XDG_CONFIG_HOME,
46
41
  path.join(hostHome, '.config')
@@ -0,0 +1,66 @@
1
+ import { defineAgentClientAdapter } from '../adapter.ts';
2
+ import { hostJoin } from '../../sandbox/engines/wsl2-paths.ts';
3
+
4
+ const traecliAdapter = defineAgentClientAdapter({
5
+ id: 'traecli',
6
+ displayName: 'TraeCode CLI',
7
+ invocation: '/${skillName}',
8
+ capabilities: {
9
+ instructions: { level: 'compatible' },
10
+ skills: { level: 'compatible' },
11
+ commands: { level: 'integrated' },
12
+ hooks: { level: 'compatible' },
13
+ subagents: { level: 'experimental' },
14
+ orchestration: { level: 'experimental' },
15
+ sandbox: { level: 'integrated' },
16
+ verification: { level: 'compatible' }
17
+ },
18
+ modelSelection: {
19
+ kind: 'interactive-only',
20
+ command: '/model',
21
+ guidance: 'Use the host model picker for the complete model and reasoning-effort catalog.'
22
+ },
23
+ delegationEvidence: {
24
+ actualModel: 'unavailable',
25
+ actualReasoningEffort: 'unavailable'
26
+ },
27
+ project: {
28
+ ownedPathPrefixes: ['.traecli/'],
29
+ managed: ['.traecli/commands/'],
30
+ merged: [],
31
+ ejected: [],
32
+ seedCommands: [{
33
+ templates: {
34
+ en: '.traecli/commands/update-agent-infra.en.md',
35
+ 'zh-CN': '.traecli/commands/update-agent-infra.zh-CN.md'
36
+ },
37
+ target: '.traecli/commands/update-agent-infra.md'
38
+ }],
39
+ customCommand: {
40
+ target: '.traecli/commands/${skillName}.md',
41
+ frontmatter: {},
42
+ argumentsToken: '$ARGUMENTS'
43
+ }
44
+ },
45
+ sandbox: {
46
+ createTool: ({ home }) => ({
47
+ id: 'traecli',
48
+ name: 'TraeCode CLI',
49
+ install: {
50
+ type: 'shell',
51
+ cmd: 'curl -fsSL https://trae.cn/trae-cli/install_v2.sh | bash'
52
+ },
53
+ sandboxBase: hostJoin(home, '.agent-infra', 'sandboxes', 'traecli'),
54
+ containerMount: '/home/devuser/.trae',
55
+ versionCmd: 'traecli --version',
56
+ setupHint: 'Run traecli login inside the container to authenticate.'
57
+ }),
58
+ aliases: [
59
+ { name: 'traecli-yolo', command: 'traecli --dangerously-bypass-approvals-and-sandbox; tput ed' },
60
+ { name: 'ty', command: 'traecli --dangerously-bypass-approvals-and-sandbox; tput ed' }
61
+ ],
62
+ hooks: []
63
+ }
64
+ });
65
+
66
+ export { traecliAdapter };