@mono-agent/agent-app 0.20.11 → 0.21.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 (369) hide show
  1. package/README.md +260 -98
  2. package/dist/adapter-send-tools.d.ts +3 -2
  3. package/dist/adapter-send-tools.d.ts.map +1 -1
  4. package/dist/adapter-send-tools.js +15 -5
  5. package/dist/adapter-send-tools.js.map +1 -1
  6. package/dist/app-controller-channels.d.ts +6 -0
  7. package/dist/app-controller-channels.d.ts.map +1 -1
  8. package/dist/app-controller-channels.js +29 -2
  9. package/dist/app-controller-channels.js.map +1 -1
  10. package/dist/app-controller-continuation.d.ts.map +1 -1
  11. package/dist/app-controller-continuation.js +2 -3
  12. package/dist/app-controller-continuation.js.map +1 -1
  13. package/dist/app-controller-lifecycle.d.ts +4 -0
  14. package/dist/app-controller-lifecycle.d.ts.map +1 -1
  15. package/dist/app-controller-lifecycle.js +7 -0
  16. package/dist/app-controller-lifecycle.js.map +1 -1
  17. package/dist/app-controller-maintenance.d.ts +3 -1
  18. package/dist/app-controller-maintenance.d.ts.map +1 -1
  19. package/dist/app-controller-maintenance.js +3 -0
  20. package/dist/app-controller-maintenance.js.map +1 -1
  21. package/dist/app-controller-monitors.d.ts +26 -0
  22. package/dist/app-controller-monitors.d.ts.map +1 -0
  23. package/dist/app-controller-monitors.js +127 -0
  24. package/dist/app-controller-monitors.js.map +1 -0
  25. package/dist/app-controller-responder.d.ts +9 -17
  26. package/dist/app-controller-responder.d.ts.map +1 -1
  27. package/dist/app-controller-responder.js +54 -86
  28. package/dist/app-controller-responder.js.map +1 -1
  29. package/dist/app-controller-traceability.d.ts.map +1 -1
  30. package/dist/app-controller-traceability.js +3 -0
  31. package/dist/app-controller-traceability.js.map +1 -1
  32. package/dist/app-controller-types.d.ts +1 -0
  33. package/dist/app-controller-types.d.ts.map +1 -1
  34. package/dist/app-controller-utils.d.ts +1 -5
  35. package/dist/app-controller-utils.d.ts.map +1 -1
  36. package/dist/app-controller-utils.js +4 -21
  37. package/dist/app-controller-utils.js.map +1 -1
  38. package/dist/app-controller.d.ts +26 -10
  39. package/dist/app-controller.d.ts.map +1 -1
  40. package/dist/app-controller.js +39 -1
  41. package/dist/app-controller.js.map +1 -1
  42. package/dist/artifact-retention.js +11 -0
  43. package/dist/artifact-retention.js.map +1 -1
  44. package/dist/background.d.ts +0 -6
  45. package/dist/background.d.ts.map +1 -1
  46. package/dist/background.js +5 -58
  47. package/dist/background.js.map +1 -1
  48. package/dist/channel-drivers/slack.d.ts.map +1 -1
  49. package/dist/channel-drivers/slack.js +18 -0
  50. package/dist/channel-drivers/slack.js.map +1 -1
  51. package/dist/channel-drivers/telegram.d.ts.map +1 -1
  52. package/dist/channel-drivers/telegram.js +26 -0
  53. package/dist/channel-drivers/telegram.js.map +1 -1
  54. package/dist/channel-drivers/tui.d.ts +68 -8
  55. package/dist/channel-drivers/tui.d.ts.map +1 -1
  56. package/dist/channel-drivers/tui.js +407 -89
  57. package/dist/channel-drivers/tui.js.map +1 -1
  58. package/dist/channel-runtime-controls.d.ts +2 -1
  59. package/dist/channel-runtime-controls.d.ts.map +1 -1
  60. package/dist/channel-runtime-controls.js +79 -22
  61. package/dist/channel-runtime-controls.js.map +1 -1
  62. package/dist/cli-args.d.ts +5 -8
  63. package/dist/cli-args.d.ts.map +1 -1
  64. package/dist/cli-args.js +33 -52
  65. package/dist/cli-args.js.map +1 -1
  66. package/dist/cli-background-command.d.ts.map +1 -1
  67. package/dist/cli-background-command.js +4 -0
  68. package/dist/cli-background-command.js.map +1 -1
  69. package/dist/cli-commands.d.ts.map +1 -1
  70. package/dist/cli-commands.js +24 -2
  71. package/dist/cli-commands.js.map +1 -1
  72. package/dist/cli-help.d.ts +26 -0
  73. package/dist/cli-help.d.ts.map +1 -1
  74. package/dist/cli-help.js +58 -53
  75. package/dist/cli-help.js.map +1 -1
  76. package/dist/cli-init-command.d.ts +1 -2
  77. package/dist/cli-init-command.d.ts.map +1 -1
  78. package/dist/cli-init-command.js +31 -71
  79. package/dist/cli-init-command.js.map +1 -1
  80. package/dist/cli-install-skill-command.d.ts.map +1 -1
  81. package/dist/cli-install-skill-command.js +12 -3
  82. package/dist/cli-install-skill-command.js.map +1 -1
  83. package/dist/config-reference.d.ts +1 -0
  84. package/dist/config-reference.d.ts.map +1 -1
  85. package/dist/config-reference.js +217 -60
  86. package/dist/config-reference.js.map +1 -1
  87. package/dist/configured-agent.d.ts +27 -4
  88. package/dist/configured-agent.d.ts.map +1 -1
  89. package/dist/configured-agent.js +159 -112
  90. package/dist/configured-agent.js.map +1 -1
  91. package/dist/conversation-title.d.ts.map +1 -1
  92. package/dist/conversation-title.js +9 -2
  93. package/dist/conversation-title.js.map +1 -1
  94. package/dist/cron-control-store.d.ts.map +1 -1
  95. package/dist/cron-control-store.js +4 -2
  96. package/dist/cron-control-store.js.map +1 -1
  97. package/dist/doctor.d.ts +7 -13
  98. package/dist/doctor.d.ts.map +1 -1
  99. package/dist/doctor.js +406 -770
  100. package/dist/doctor.js.map +1 -1
  101. package/dist/first-run-readiness.d.ts.map +1 -1
  102. package/dist/first-run-readiness.js +0 -6
  103. package/dist/first-run-readiness.js.map +1 -1
  104. package/dist/index.d.ts +2 -0
  105. package/dist/index.d.ts.map +1 -1
  106. package/dist/index.js +1 -0
  107. package/dist/index.js.map +1 -1
  108. package/dist/interaction-bridge.d.ts +3 -3
  109. package/dist/interaction-bridge.d.ts.map +1 -1
  110. package/dist/interaction-bridge.js +27 -10
  111. package/dist/interaction-bridge.js.map +1 -1
  112. package/dist/launchd.d.ts +2 -0
  113. package/dist/launchd.d.ts.map +1 -1
  114. package/dist/launchd.js +3 -0
  115. package/dist/launchd.js.map +1 -1
  116. package/dist/local-tui-session.d.ts +14 -0
  117. package/dist/local-tui-session.d.ts.map +1 -0
  118. package/dist/local-tui-session.js +100 -0
  119. package/dist/local-tui-session.js.map +1 -0
  120. package/dist/mcp-apps.d.ts.map +1 -1
  121. package/dist/mcp-apps.js +3 -0
  122. package/dist/mcp-apps.js.map +1 -1
  123. package/dist/memory-journal.d.ts +53 -0
  124. package/dist/memory-journal.d.ts.map +1 -0
  125. package/dist/memory-journal.js +586 -0
  126. package/dist/memory-journal.js.map +1 -0
  127. package/dist/memory-recall.d.ts.map +1 -1
  128. package/dist/memory-recall.js +16 -2
  129. package/dist/memory-recall.js.map +1 -1
  130. package/dist/memory-remember.d.ts +49 -0
  131. package/dist/memory-remember.d.ts.map +1 -0
  132. package/dist/memory-remember.js +190 -0
  133. package/dist/memory-remember.js.map +1 -0
  134. package/dist/memory-retrieval.d.ts +33 -0
  135. package/dist/memory-retrieval.d.ts.map +1 -1
  136. package/dist/memory-retrieval.js +43 -0
  137. package/dist/memory-retrieval.js.map +1 -1
  138. package/dist/model-effort-capabilities.d.ts +8 -9
  139. package/dist/model-effort-capabilities.d.ts.map +1 -1
  140. package/dist/model-effort-capabilities.js +17 -35
  141. package/dist/model-effort-capabilities.js.map +1 -1
  142. package/dist/modules/base.d.ts +3 -4
  143. package/dist/modules/base.d.ts.map +1 -1
  144. package/dist/modules/base.js +4 -6
  145. package/dist/modules/base.js.map +1 -1
  146. package/dist/modules/catalog.d.ts.map +1 -1
  147. package/dist/modules/catalog.js +11 -9
  148. package/dist/modules/catalog.js.map +1 -1
  149. package/dist/modules/known-tools.d.ts +2 -2
  150. package/dist/modules/known-tools.d.ts.map +1 -1
  151. package/dist/modules/known-tools.js +7 -0
  152. package/dist/modules/known-tools.js.map +1 -1
  153. package/dist/monitor-channel-routing.d.ts +20 -0
  154. package/dist/monitor-channel-routing.d.ts.map +1 -0
  155. package/dist/monitor-channel-routing.js +73 -0
  156. package/dist/monitor-channel-routing.js.map +1 -0
  157. package/dist/monitors-command.d.ts +23 -0
  158. package/dist/monitors-command.d.ts.map +1 -0
  159. package/dist/monitors-command.js +217 -0
  160. package/dist/monitors-command.js.map +1 -0
  161. package/dist/monitors-config.d.ts +77 -0
  162. package/dist/monitors-config.d.ts.map +1 -0
  163. package/dist/monitors-config.js +150 -0
  164. package/dist/monitors-config.js.map +1 -0
  165. package/dist/monitors-context.d.ts +58 -0
  166. package/dist/monitors-context.d.ts.map +1 -0
  167. package/dist/monitors-context.js +194 -0
  168. package/dist/monitors-context.js.map +1 -0
  169. package/dist/monitors-runtime.d.ts +36 -0
  170. package/dist/monitors-runtime.d.ts.map +1 -0
  171. package/dist/monitors-runtime.js +103 -0
  172. package/dist/monitors-runtime.js.map +1 -0
  173. package/dist/monitors-service.d.ts +71 -0
  174. package/dist/monitors-service.d.ts.map +1 -0
  175. package/dist/monitors-service.js +1796 -0
  176. package/dist/monitors-service.js.map +1 -0
  177. package/dist/monitors-store.d.ts +93 -0
  178. package/dist/monitors-store.d.ts.map +1 -0
  179. package/dist/monitors-store.js +313 -0
  180. package/dist/monitors-store.js.map +1 -0
  181. package/dist/notify-destinations.d.ts +3 -2
  182. package/dist/notify-destinations.d.ts.map +1 -1
  183. package/dist/notify-destinations.js +6 -7
  184. package/dist/notify-destinations.js.map +1 -1
  185. package/dist/posted-reply-history.d.ts.map +1 -1
  186. package/dist/posted-reply-history.js +40 -3
  187. package/dist/posted-reply-history.js.map +1 -1
  188. package/dist/proactive-notify.d.ts +20 -1
  189. package/dist/proactive-notify.d.ts.map +1 -1
  190. package/dist/proactive-notify.js +56 -3
  191. package/dist/proactive-notify.js.map +1 -1
  192. package/dist/process-job-channel-routing.js +2 -1
  193. package/dist/process-job-channel-routing.js.map +1 -1
  194. package/dist/process-job-output-tail.d.ts +53 -0
  195. package/dist/process-job-output-tail.d.ts.map +1 -0
  196. package/dist/process-job-output-tail.js +257 -0
  197. package/dist/process-job-output-tail.js.map +1 -0
  198. package/dist/process-jobs-config.d.ts +1 -1
  199. package/dist/process-jobs-config.js +1 -1
  200. package/dist/process-jobs-config.js.map +1 -1
  201. package/dist/process-jobs-context.d.ts +11 -1
  202. package/dist/process-jobs-context.d.ts.map +1 -1
  203. package/dist/process-jobs-context.js +55 -11
  204. package/dist/process-jobs-context.js.map +1 -1
  205. package/dist/process-jobs-protection.js +1 -1
  206. package/dist/process-jobs-protection.js.map +1 -1
  207. package/dist/process-jobs-runtime.d.ts.map +1 -1
  208. package/dist/process-jobs-runtime.js +15 -12
  209. package/dist/process-jobs-runtime.js.map +1 -1
  210. package/dist/process-jobs-service.d.ts.map +1 -1
  211. package/dist/process-jobs-service.js +118 -172
  212. package/dist/process-jobs-service.js.map +1 -1
  213. package/dist/process-jobs-store.d.ts +3 -1
  214. package/dist/process-jobs-store.d.ts.map +1 -1
  215. package/dist/process-jobs-store.js +4 -1
  216. package/dist/process-jobs-store.js.map +1 -1
  217. package/dist/process-output-redaction.d.ts +58 -0
  218. package/dist/process-output-redaction.d.ts.map +1 -0
  219. package/dist/process-output-redaction.js +311 -0
  220. package/dist/process-output-redaction.js.map +1 -0
  221. package/dist/project-skills.d.ts +11 -5
  222. package/dist/project-skills.d.ts.map +1 -1
  223. package/dist/project-skills.js +88 -39
  224. package/dist/project-skills.js.map +1 -1
  225. package/dist/provider-auth-checks.d.ts +27 -0
  226. package/dist/provider-auth-checks.d.ts.map +1 -0
  227. package/dist/provider-auth-checks.js +349 -0
  228. package/dist/provider-auth-checks.js.map +1 -0
  229. package/dist/provider-auth-observations.d.ts +22 -0
  230. package/dist/provider-auth-observations.d.ts.map +1 -0
  231. package/dist/provider-auth-observations.js +139 -0
  232. package/dist/provider-auth-observations.js.map +1 -0
  233. package/dist/provider-auth-operator.d.ts +19 -0
  234. package/dist/provider-auth-operator.d.ts.map +1 -0
  235. package/dist/provider-auth-operator.js +560 -0
  236. package/dist/provider-auth-operator.js.map +1 -0
  237. package/dist/provider-auth-status.d.ts +20 -0
  238. package/dist/provider-auth-status.d.ts.map +1 -0
  239. package/dist/provider-auth-status.js +235 -0
  240. package/dist/provider-auth-status.js.map +1 -0
  241. package/dist/provider-model-catalog.d.ts +95 -0
  242. package/dist/provider-model-catalog.d.ts.map +1 -0
  243. package/dist/provider-model-catalog.js +550 -0
  244. package/dist/provider-model-catalog.js.map +1 -0
  245. package/dist/provider-setup.d.ts +26 -13
  246. package/dist/provider-setup.d.ts.map +1 -1
  247. package/dist/provider-setup.js +106 -130
  248. package/dist/provider-setup.js.map +1 -1
  249. package/dist/readiness-probe-worker.d.ts +1 -2
  250. package/dist/readiness-probe-worker.d.ts.map +1 -1
  251. package/dist/readiness-probe-worker.js +3 -8
  252. package/dist/readiness-probe-worker.js.map +1 -1
  253. package/dist/readiness-probe.d.ts +1 -1
  254. package/dist/readiness-probe.d.ts.map +1 -1
  255. package/dist/readiness-probe.js +3 -33
  256. package/dist/readiness-probe.js.map +1 -1
  257. package/dist/reply-artifacts.d.ts +3 -1
  258. package/dist/reply-artifacts.d.ts.map +1 -1
  259. package/dist/reply-artifacts.js +45 -10
  260. package/dist/reply-artifacts.js.map +1 -1
  261. package/dist/request-model-override.d.ts +14 -37
  262. package/dist/request-model-override.d.ts.map +1 -1
  263. package/dist/request-model-override.js +105 -143
  264. package/dist/request-model-override.js.map +1 -1
  265. package/dist/request-scoped-mcp.d.ts +3 -0
  266. package/dist/request-scoped-mcp.d.ts.map +1 -1
  267. package/dist/request-scoped-mcp.js +1 -1
  268. package/dist/request-scoped-mcp.js.map +1 -1
  269. package/dist/run-history.d.ts.map +1 -1
  270. package/dist/run-history.js +56 -13
  271. package/dist/run-history.js.map +1 -1
  272. package/dist/runtime-option-extensions.d.ts +2 -4
  273. package/dist/runtime-option-extensions.d.ts.map +1 -1
  274. package/dist/runtime-option-extensions.js +4 -8
  275. package/dist/runtime-option-extensions.js.map +1 -1
  276. package/dist/runtime-routes.d.ts +5 -5
  277. package/dist/runtime-routes.d.ts.map +1 -1
  278. package/dist/runtime-routes.js +29 -18
  279. package/dist/runtime-routes.js.map +1 -1
  280. package/dist/sandbox-settings-cleanup.d.ts +15 -0
  281. package/dist/sandbox-settings-cleanup.d.ts.map +1 -0
  282. package/dist/sandbox-settings-cleanup.js +88 -0
  283. package/dist/sandbox-settings-cleanup.js.map +1 -0
  284. package/dist/seen-conversations.d.ts +4 -3
  285. package/dist/seen-conversations.d.ts.map +1 -1
  286. package/dist/seen-conversations.js +6 -5
  287. package/dist/seen-conversations.js.map +1 -1
  288. package/dist/session-history.d.ts +14 -0
  289. package/dist/session-history.d.ts.map +1 -1
  290. package/dist/session-history.js +120 -5
  291. package/dist/session-history.js.map +1 -1
  292. package/dist/systemd-command.d.ts +8 -0
  293. package/dist/systemd-command.d.ts.map +1 -0
  294. package/dist/systemd-command.js +206 -0
  295. package/dist/systemd-command.js.map +1 -0
  296. package/dist/systemd.d.ts +51 -0
  297. package/dist/systemd.d.ts.map +1 -0
  298. package/dist/systemd.js +299 -0
  299. package/dist/systemd.js.map +1 -0
  300. package/dist/tool-output-artifacts.d.ts +4 -0
  301. package/dist/tool-output-artifacts.d.ts.map +1 -0
  302. package/dist/tool-output-artifacts.js +17 -0
  303. package/dist/tool-output-artifacts.js.map +1 -0
  304. package/dist/trigger-overrides.d.ts +6 -0
  305. package/dist/trigger-overrides.d.ts.map +1 -1
  306. package/dist/trigger-overrides.js +36 -4
  307. package/dist/trigger-overrides.js.map +1 -1
  308. package/dist/tui-command.d.ts +0 -45
  309. package/dist/tui-command.d.ts.map +1 -1
  310. package/dist/tui-command.js +27 -264
  311. package/dist/tui-command.js.map +1 -1
  312. package/dist/untrusted-text.d.ts +36 -0
  313. package/dist/untrusted-text.d.ts.map +1 -0
  314. package/dist/untrusted-text.js +150 -0
  315. package/dist/untrusted-text.js.map +1 -0
  316. package/dist/web-command.d.ts +3 -0
  317. package/dist/web-command.d.ts.map +1 -1
  318. package/dist/web-command.js +112 -7
  319. package/dist/web-command.js.map +1 -1
  320. package/dist/web-request-coordinator.d.ts +19 -0
  321. package/dist/web-request-coordinator.d.ts.map +1 -0
  322. package/dist/web-request-coordinator.js +242 -0
  323. package/dist/web-request-coordinator.js.map +1 -0
  324. package/dist/wizard/answers.d.ts +3 -9
  325. package/dist/wizard/answers.d.ts.map +1 -1
  326. package/dist/wizard/answers.js +11 -36
  327. package/dist/wizard/answers.js.map +1 -1
  328. package/dist/wizard/from-flags.d.ts +1 -2
  329. package/dist/wizard/from-flags.d.ts.map +1 -1
  330. package/dist/wizard/from-flags.js +8 -3
  331. package/dist/wizard/from-flags.js.map +1 -1
  332. package/dist/wizard/model-discovery.d.ts +7 -8
  333. package/dist/wizard/model-discovery.d.ts.map +1 -1
  334. package/dist/wizard/model-discovery.js +58 -431
  335. package/dist/wizard/model-discovery.js.map +1 -1
  336. package/dist/wizard/presets.js +2 -2
  337. package/dist/wizard/presets.js.map +1 -1
  338. package/dist/wizard/prompts.d.ts +13 -12
  339. package/dist/wizard/prompts.d.ts.map +1 -1
  340. package/dist/wizard/prompts.js +25 -45
  341. package/dist/wizard/prompts.js.map +1 -1
  342. package/dist/wizard/run.d.ts.map +1 -1
  343. package/dist/wizard/run.js +30 -153
  344. package/dist/wizard/run.js.map +1 -1
  345. package/package.json +18 -18
  346. package/schema/mono-agent.config.schema.json +301 -53
  347. package/skills/mono-agent-composer/SKILL.md +5 -5
  348. package/skills/mono-agent-composer/references/config-blueprint.md +61 -47
  349. package/skills/mono-agent-composer/references/discovery-questions.md +18 -18
  350. package/skills/mono-agent-composer/references/feature-coverage.md +39 -21
  351. package/skills/mono-agent-composer/references/package-map.md +26 -17
  352. package/skills/mono-agent-composer/references/playbooks.md +39 -28
  353. package/skills/mono-agent-composer/references/validation.md +4 -3
  354. package/dist/codex-model-catalog.d.ts +0 -15
  355. package/dist/codex-model-catalog.d.ts.map +0 -1
  356. package/dist/codex-model-catalog.js +0 -220
  357. package/dist/codex-model-catalog.js.map +0 -1
  358. package/dist/configuration-proposal-main.d.ts +0 -3
  359. package/dist/configuration-proposal-main.d.ts.map +0 -1
  360. package/dist/configuration-proposal-main.js +0 -13
  361. package/dist/configuration-proposal-main.js.map +0 -1
  362. package/dist/configuration-proposal-tool.d.ts +0 -33
  363. package/dist/configuration-proposal-tool.d.ts.map +0 -1
  364. package/dist/configuration-proposal-tool.js +0 -188
  365. package/dist/configuration-proposal-tool.js.map +0 -1
  366. package/dist/local-configuration.d.ts +0 -99
  367. package/dist/local-configuration.d.ts.map +0 -1
  368. package/dist/local-configuration.js +0 -1330
  369. package/dist/local-configuration.js.map +0 -1
@@ -13,11 +13,6 @@ export interface ProviderSetupPiLoginAction extends ProviderSetupCommandAction {
13
13
  readonly id: `pi-login:${string}`;
14
14
  readonly piAuthPath: string;
15
15
  }
16
- export type CodexLoginMode = "browser" | "device";
17
- export interface ProviderSetupCodexLoginAction extends ProviderSetupCommandAction {
18
- readonly id: "codex-login";
19
- readonly authMode: CodexLoginMode;
20
- }
21
16
  export interface ProviderSetupHttpAction {
22
17
  readonly id: string;
23
18
  readonly kind: ProviderSetupKind;
@@ -39,7 +34,7 @@ export interface ProviderSetupPiApiKeyAction {
39
34
  readonly cwd: string;
40
35
  readonly detail: string;
41
36
  }
42
- export type ProviderSetupAction = ProviderSetupPiLoginAction | ProviderSetupCodexLoginAction | ProviderSetupCommandAction | ProviderSetupHttpAction | ProviderSetupPiApiKeyAction;
37
+ export type ProviderSetupAction = ProviderSetupPiLoginAction | ProviderSetupCommandAction | ProviderSetupHttpAction | ProviderSetupPiApiKeyAction;
43
38
  export interface ProviderSetupPlan {
44
39
  readonly actions: readonly ProviderSetupAction[];
45
40
  /** Auth actions omitted because a credential/sign-in was detected. */
@@ -75,12 +70,10 @@ export interface PlanProviderSetupOptions {
75
70
  readonly piAuthPath?: string;
76
71
  /** Internal test seam for verifying bundled Pi CLI resolution in packed layouts. */
77
72
  readonly piCliPath?: string;
78
- /** Credential/status observations keyed by `claude`, `codex`, `pi:<provider>`, or provider id. */
73
+ /** Credential/status observations keyed by provider id or exact model reference. */
79
74
  readonly credentialStates?: Readonly<Record<string, ProviderCredentialState | undefined>>;
80
75
  /** Explicit repair path: rerun authentication even when a credential was detected. */
81
76
  readonly forceAuthentication?: boolean;
82
- /** Direct Codex never guesses headless mode; callers select this explicitly. */
83
- readonly codexAuthMode?: CodexLoginMode;
84
77
  /** Select OAuth or API-key setup for Pi providers that support both. */
85
78
  readonly piAuthMethods?: Readonly<Record<string, "oauth" | "api-key" | undefined>>;
86
79
  /** API keys can be used from env without being copied into Pi's secure store. */
@@ -119,6 +112,21 @@ export interface ExecuteProviderSetupOptions {
119
112
  /** Stop before launching the next independent action after user interruption. */
120
113
  readonly abortSignal?: AbortSignal;
121
114
  }
115
+ type PiAuthPromotionHooks = Pick<ExecuteProviderSetupOptions, "beforePiAuthPromotion" | "afterPiAuthLink" | "beforeStalePiAuthLockRemoval" | "afterStalePiAuthLockRemoval" | "beforePiAuthCleanup" | "afterPiAuthLockCreated" | "beforePiAuthMissingLockSync" | "beforePiAuthTempCleanup" | "beforePiAuthBackupCleanup" | "beforePiAuthPostMutationSync">;
116
+ export interface PersistPiProviderCredentialOptions extends PiAuthPromotionHooks {
117
+ readonly authPath: string;
118
+ readonly provider: string;
119
+ readonly platform?: NodeJS.Platform;
120
+ /**
121
+ * Called only while the cross-process auth-store lock is held. The returned
122
+ * credential is validated, merged into the latest store snapshot, and never
123
+ * included in an error message.
124
+ */
125
+ readonly resolveCredential: (signal?: AbortSignal) => Promise<unknown>;
126
+ readonly abortSignal?: AbortSignal;
127
+ /** Secret-free signal that target-store mutation began; the callback must not throw. */
128
+ readonly onCredentialStoreMutation?: () => void;
129
+ }
122
130
  export declare function resolvePiCliPath(): string;
123
131
  export declare function piLoginCommand(provider: string, piCliPath?: string): readonly [string, ...string[]];
124
132
  export declare function piAuthRecoveryCommand(provider: string, piAuthPath?: string): string;
@@ -130,14 +138,12 @@ export declare function piAuthPathForSetup(piAuthPath: string | undefined, cwd?:
130
138
  * to `verified`.
131
139
  */
132
140
  export declare function detectProviderCredentialStates(options: DetectProviderCredentialStatesOptions): Promise<Readonly<Record<string, ProviderCredentialState>>>;
133
- /** Whether a selected route has a credential in the destination agent's durable environment. */
134
- export declare function hasDurableProviderEnvironmentCredential(rawModelRef: string, persistedEnv: Readonly<Record<string, string | undefined>>): boolean;
135
141
  /**
136
142
  * Build the minimal operational environment needed to inspect durable CLI login
137
143
  * state. A positive allowlist prevents unrelated shell credentials from being
138
- * inherited by Codex or Claude while retaining their standard config roots.
144
+ * inherited by provider discovery commands.
139
145
  */
140
- export declare function credentialNeutralProviderStatusEnvironment(source?: Readonly<Record<string, string | undefined>>, durableEnvironment?: Readonly<Record<string, string | undefined>>): Record<string, string | undefined>;
146
+ export declare function credentialNeutralProviderStatusEnvironment(source?: Readonly<Record<string, string | undefined>>, _durableEnvironment?: Readonly<Record<string, string | undefined>>): Record<string, string | undefined>;
141
147
  export interface BoundedProviderCommandResult {
142
148
  readonly stdout: string;
143
149
  }
@@ -159,6 +165,12 @@ export declare function providerSetupActionCommandLine(action: ProviderSetupActi
159
165
  export declare function isProviderSetupPiApiKeyAction(action: ProviderSetupAction): action is ProviderSetupPiApiKeyAction;
160
166
  export declare function isProviderSetupPiLoginAction(action: ProviderSetupAction): action is ProviderSetupPiLoginAction;
161
167
  export declare function executeProviderSetupPlan(plan: ProviderSetupPlan, options?: ExecuteProviderSetupOptions): Promise<ProviderSetupResult[]>;
168
+ /**
169
+ * The single mutation path for Pi provider credentials. Login remains inside
170
+ * the lock so two processes cannot both authenticate from the same snapshot
171
+ * and silently clobber each other's successful result.
172
+ */
173
+ export declare function persistPiProviderCredential(options: PersistPiProviderCredentialOptions): Promise<void>;
162
174
  export type StalePiAuthLockRepairResult = "removed" | "active" | "unverifiable";
163
175
  /**
164
176
  * Remove only a secure, identity-stable lock whose recorded process is proven
@@ -171,4 +183,5 @@ export declare function repairStalePiAuthLock(path: string, ownerUid: number, op
171
183
  readonly beforeRemoval?: (lockPath: string) => void | Promise<void>;
172
184
  readonly afterRemoval?: (lockPath: string) => void | Promise<void>;
173
185
  }): Promise<StalePiAuthLockRepairResult>;
186
+ export {};
174
187
  //# sourceMappingURL=provider-setup.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"provider-setup.d.ts","sourceRoot":"","sources":["../src/provider-setup.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"provider-setup.d.ts","sourceRoot":"","sources":["../src/provider-setup.ts"],"names":[],"mappings":"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"}
@@ -8,18 +8,12 @@ import { isDeepStrictEqual } from "node:util";
8
8
  import { fileURLToPath } from "node:url";
9
9
  import { builtinModels } from "@earendil-works/pi-ai/providers/all";
10
10
  import { modelReferenceKey, parseMonoRuntimeModelReference } from "@mono-agent/runtime-adapter";
11
- import { inspectPiAuthStore } from "./pi-auth-store-inspection.js";
11
+ import { inspectPiAuthStore, MAX_PI_AUTH_STORE_BYTES } from "./pi-auth-store-inspection.js";
12
12
  const DEFAULT_PI_AUTH_PATH = join(homedir(), ".pi", "agent", "auth.json");
13
13
  const PI_API_KEY_PROVIDERS = {
14
14
  "opencode-go": "OPENCODE_API_KEY",
15
15
  };
16
- const DIRECT_PROVIDER_CREDENTIAL_ENV_KEYS = {
17
- codex: ["OPENAI_API_KEY"],
18
- claude: ["ANTHROPIC_API_KEY", "ANTHROPIC_AUTH_TOKEN", "CLAUDE_CODE_OAUTH_TOKEN"],
19
- };
20
16
  const PROVIDER_STATUS_SECRET_ENV_KEYS = [
21
- ...DIRECT_PROVIDER_CREDENTIAL_ENV_KEYS.codex,
22
- ...DIRECT_PROVIDER_CREDENTIAL_ENV_KEYS.claude,
23
17
  ...Object.values(PI_API_KEY_PROVIDERS),
24
18
  ];
25
19
  const PROVIDER_STATUS_ENV_ALLOWLIST = new Set([
@@ -107,86 +101,29 @@ export async function detectProviderCredentialStates(options) {
107
101
  return [];
108
102
  }
109
103
  });
110
- const timeout = typeof options.timeoutMs === "number" && Number.isFinite(options.timeoutMs) && options.timeoutMs > 0
111
- ? Math.trunc(options.timeoutMs)
112
- : 2_000;
113
- const run = options.execFile ?? runProviderStatusCommand;
114
104
  const persistedEnv = options.persistedEnv ?? {};
115
- const statusEnv = credentialNeutralProviderStatusEnvironment(process.env, persistedEnv);
116
- const checks = [];
117
- if (refs.some((ref) => ref.sdk === "codex")) {
118
- if (hasAnyNonEmptyPersistedValue(persistedEnv, DIRECT_PROVIDER_CREDENTIAL_ENV_KEYS.codex)) {
119
- states.codex = "credential_detected";
120
- }
121
- else {
122
- checks.push(run("codex", ["login", "status"], {
123
- cwd: options.cwd,
124
- timeout,
125
- env: statusEnv,
126
- ...(options.abortSignal === undefined ? {} : { abortSignal: options.abortSignal }),
127
- }).then(() => { states.codex = "credential_detected"; }, () => { states.codex = "auth_required"; }));
128
- }
129
- }
130
- if (refs.some((ref) => ref.sdk === "claude")) {
131
- if (hasAnyNonEmptyPersistedValue(persistedEnv, DIRECT_PROVIDER_CREDENTIAL_ENV_KEYS.claude)) {
132
- states.claude = "credential_detected";
133
- }
134
- else {
135
- checks.push(run("claude", ["auth", "status", "--json"], {
136
- cwd: options.cwd,
137
- timeout,
138
- env: statusEnv,
139
- ...(options.abortSignal === undefined ? {} : { abortSignal: options.abortSignal }),
140
- }).then(() => { states.claude = "credential_detected"; }, () => { states.claude = "auth_required"; }));
141
- }
142
- }
143
- const piProviders = new Set(refs.filter((ref) => ref.sdk === "pi" && typeof ref.provider === "string")
144
- .map((ref) => ref.provider));
105
+ const piProviders = new Set(refs.map((ref) => ref.provider));
145
106
  if (piProviders.size > 0) {
146
107
  const detected = await safelyDetectedPiCredentialProviders(piAuthPathForSetup(options.piAuthPath, options.cwd));
147
108
  for (const provider of piProviders) {
148
109
  const apiKeyEnv = PI_API_KEY_PROVIDERS[provider];
149
- states[`pi:${provider}`] = detected.has(provider)
110
+ states[provider] = detected.has(provider)
150
111
  || (apiKeyEnv !== undefined && hasNonEmptyPersistedValue(persistedEnv[apiKeyEnv]))
151
112
  ? "credential_detected"
152
113
  : "auth_required";
153
114
  }
154
115
  }
155
- await Promise.all(checks);
156
116
  return states;
157
117
  }
158
- /** Whether a selected route has a credential in the destination agent's durable environment. */
159
- export function hasDurableProviderEnvironmentCredential(rawModelRef, persistedEnv) {
160
- let ref;
161
- try {
162
- ref = parseMonoRuntimeModelReference(rawModelRef);
163
- }
164
- catch {
165
- return false;
166
- }
167
- if (ref.sdk === "codex") {
168
- return hasAnyNonEmptyPersistedValue(persistedEnv, DIRECT_PROVIDER_CREDENTIAL_ENV_KEYS.codex);
169
- }
170
- if (ref.sdk === "claude") {
171
- return hasAnyNonEmptyPersistedValue(persistedEnv, DIRECT_PROVIDER_CREDENTIAL_ENV_KEYS.claude);
172
- }
173
- if (ref.sdk !== "pi" || typeof ref.provider !== "string")
174
- return false;
175
- const apiKeyEnv = PI_API_KEY_PROVIDERS[ref.provider];
176
- return apiKeyEnv !== undefined && hasNonEmptyPersistedValue(persistedEnv[apiKeyEnv]);
177
- }
178
- function hasAnyNonEmptyPersistedValue(persistedEnv, names) {
179
- return names.some((name) => hasNonEmptyPersistedValue(persistedEnv[name]));
180
- }
181
118
  function hasNonEmptyPersistedValue(value) {
182
119
  return value !== undefined && value.trim().length > 0;
183
120
  }
184
121
  /**
185
122
  * Build the minimal operational environment needed to inspect durable CLI login
186
123
  * state. A positive allowlist prevents unrelated shell credentials from being
187
- * inherited by Codex or Claude while retaining their standard config roots.
124
+ * inherited by provider discovery commands.
188
125
  */
189
- export function credentialNeutralProviderStatusEnvironment(source = process.env, durableEnvironment = {}) {
126
+ export function credentialNeutralProviderStatusEnvironment(source = process.env, _durableEnvironment = {}) {
190
127
  const sanitized = {};
191
128
  for (const [name, value] of Object.entries(source)) {
192
129
  const normalizedName = name.toUpperCase();
@@ -195,18 +132,10 @@ export function credentialNeutralProviderStatusEnvironment(source = process.env,
195
132
  sanitized[name] = value;
196
133
  }
197
134
  }
198
- for (const name of ["CLAUDE_CONFIG_DIR", "CODEX_HOME"]) {
199
- const value = durableEnvironment[name];
200
- if (hasNonEmptyPersistedValue(value))
201
- sanitized[name] = value;
202
- }
203
135
  for (const name of PROVIDER_STATUS_SECRET_ENV_KEYS)
204
136
  delete sanitized[name];
205
137
  return sanitized;
206
138
  }
207
- function runProviderStatusCommand(file, args, options) {
208
- return runBoundedProviderCommand(file, args, options).then(() => undefined);
209
- }
210
139
  /**
211
140
  * Run a non-interactive provider probe with a hard process-lifecycle bound.
212
141
  * Node's execFile timeout sends only SIGTERM and can wait forever when a CLI
@@ -360,46 +289,7 @@ export function planProviderSetup(options) {
360
289
  modelRefs: [...new Set([...existing.modelRefs, ...action.modelRefs])],
361
290
  });
362
291
  };
363
- if (ref.sdk === "claude") {
364
- if (authAlreadyDetected(["claude", refKey])) {
365
- detectedModelRefs.add(refKey);
366
- continue;
367
- }
368
- add({
369
- id: "claude-login",
370
- kind: "auth",
371
- label: "Claude login",
372
- modelRefs: [refKey],
373
- command: ["claude", "/login"],
374
- cwd: options.cwd,
375
- detail: "Runs the Claude Code login flow for Claude model references.",
376
- });
377
- continue;
378
- }
379
- if (ref.sdk === "codex") {
380
- if (authAlreadyDetected(["codex", refKey])) {
381
- detectedModelRefs.add(refKey);
382
- continue;
383
- }
384
- const authMode = options.codexAuthMode ?? "browser";
385
- add({
386
- id: "codex-login",
387
- kind: "auth",
388
- label: "Codex login",
389
- modelRefs: [refKey],
390
- command: authMode === "device" ? ["codex", "login", "--device-auth"] : ["codex", "login"],
391
- authMode,
392
- cwd: options.cwd,
393
- detail: authMode === "device"
394
- ? "Runs Codex device-code login for a remote or headless machine."
395
- : "Runs Codex browser login with a localhost callback server.",
396
- });
397
- continue;
398
- }
399
- if (ref.sdk !== "pi" || typeof ref.provider !== "string") {
400
- continue;
401
- }
402
- if (authAlreadyDetected([`pi:${ref.provider}`, ref.provider, refKey])) {
292
+ if (authAlreadyDetected([ref.provider, refKey])) {
403
293
  detectedModelRefs.add(refKey);
404
294
  continue;
405
295
  }
@@ -532,15 +422,13 @@ async function runPiApiKeyAction(action, apiKeys, platform, hooks) {
532
422
  };
533
423
  }
534
424
  try {
535
- assertOwnerOnlyPersistenceSupported(platform);
536
- await withPiAuthFileLock(action.piAuthPath, async (authPath, ownerUid, assertLockHeld) => {
537
- const original = await readPiAuthStore(authPath, piAuthSingleLinkPolicy(ownerUid));
538
- const next = {
539
- ...original.auth,
540
- [action.provider]: { type: "api_key", key },
541
- };
542
- await writePiAuthStoreAtomically(authPath, next, original, ownerUid, assertLockHeld, hooks);
543
- }, hooks);
425
+ await persistPiProviderCredential({
426
+ authPath: action.piAuthPath,
427
+ provider: action.provider,
428
+ platform,
429
+ resolveCredential: async () => ({ type: "api_key", key }),
430
+ ...hooks,
431
+ });
544
432
  return {
545
433
  action,
546
434
  status: "ok",
@@ -556,6 +444,55 @@ async function runPiApiKeyAction(action, apiKeys, platform, hooks) {
556
444
  };
557
445
  }
558
446
  }
447
+ /**
448
+ * The single mutation path for Pi provider credentials. Login remains inside
449
+ * the lock so two processes cannot both authenticate from the same snapshot
450
+ * and silently clobber each other's successful result.
451
+ */
452
+ export async function persistPiProviderCredential(options) {
453
+ assertOwnerOnlyPersistenceSupported(options.platform ?? process.platform);
454
+ const hooks = options;
455
+ await withPiAuthFileLock(options.authPath, async (authPath, ownerUid, assertLockHeld) => {
456
+ const original = await readPiAuthStore(authPath, piAuthSingleLinkPolicy(ownerUid));
457
+ throwIfProviderAuthAborted(options.abortSignal);
458
+ const credential = await resolveProviderCredentialWithAbort(options.resolveCredential, options.abortSignal);
459
+ throwIfProviderAuthAborted(options.abortSignal);
460
+ if (!isUsableStoredPiCredential(options.provider, credential)) {
461
+ throw new Error(`Provider authentication returned an invalid credential for ${options.provider}.`);
462
+ }
463
+ const next = { ...original.auth, [options.provider]: credential };
464
+ if (!isBoundedCredentialValue(next)) {
465
+ throw new Error(`Provider authentication would exceed the Pi credential store safety limit for ${options.provider}.`);
466
+ }
467
+ await writePiAuthStoreAtomically(authPath, next, original, ownerUid, assertLockHeld, hooks, options.abortSignal, options.onCredentialStoreMutation);
468
+ }, hooks);
469
+ }
470
+ async function resolveProviderCredentialWithAbort(resolveCredential, signal) {
471
+ throwIfProviderAuthAborted(signal);
472
+ const pending = Promise.resolve().then(async () => await resolveCredential(signal));
473
+ if (signal === undefined)
474
+ return await pending;
475
+ return await new Promise((resolve, reject) => {
476
+ let settled = false;
477
+ const finish = (callback) => {
478
+ if (settled)
479
+ return;
480
+ settled = true;
481
+ signal.removeEventListener("abort", abort);
482
+ callback();
483
+ };
484
+ const abort = () => finish(() => reject(signal.reason ?? new Error("Provider authentication was cancelled.")));
485
+ signal.addEventListener("abort", abort, { once: true });
486
+ if (signal.aborted)
487
+ abort();
488
+ pending.then((credential) => finish(() => resolve(credential)), (error) => finish(() => reject(error)));
489
+ });
490
+ }
491
+ function throwIfProviderAuthAborted(signal) {
492
+ if (signal?.aborted === true) {
493
+ throw signal.reason ?? new Error("Provider authentication was cancelled.");
494
+ }
495
+ }
559
496
  function isBoundedCredentialString(value) {
560
497
  return typeof value === "string"
561
498
  && value.trim().length > 0
@@ -565,10 +502,32 @@ function isBoundedCredentialString(value) {
565
502
  function isUsableStoredPiCredential(_provider, value) {
566
503
  if (!isRecord(value))
567
504
  return false;
505
+ if (!isBoundedCredentialValue(value))
506
+ return false;
568
507
  if (value.type === "oauth") {
569
- return isBoundedCredentialString(value.access) || isBoundedCredentialString(value.refresh);
508
+ return (isBoundedCredentialString(value.access) || isBoundedCredentialString(value.refresh))
509
+ && (value.expires === undefined || (typeof value.expires === "number" && Number.isFinite(value.expires)));
510
+ }
511
+ if (value.type !== "api_key")
512
+ return false;
513
+ if (Object.keys(value).some((key) => key !== "type" && key !== "key" && key !== "env"))
514
+ return false;
515
+ if (isBoundedCredentialString(value.key))
516
+ return true;
517
+ if (value.env === undefined)
518
+ return Object.keys(value).length === 1;
519
+ if (!isRecord(value.env))
520
+ return false;
521
+ const entries = Object.entries(value.env);
522
+ return entries.length > 0 && entries.length <= 64 && entries.every(([key, entry]) => /^[A-Z][A-Z0-9_]{0,127}$/u.test(key) && isBoundedCredentialString(entry));
523
+ }
524
+ function isBoundedCredentialValue(value) {
525
+ try {
526
+ return Buffer.byteLength(JSON.stringify(value), "utf8") <= MAX_PI_AUTH_STORE_BYTES;
527
+ }
528
+ catch {
529
+ return false;
570
530
  }
571
- return value.type === "api_key" && isBoundedCredentialString(value.key);
572
531
  }
573
532
  async function runCommandAction(action, spawnImpl, platform, hooks, preflightTimeoutMs, abortSignal) {
574
533
  if (isProviderSetupPiLoginAction(action)) {
@@ -1153,19 +1112,26 @@ function assertPiAuthStoreStat(path, value, policy) {
1153
1112
  throw new Error(`Refusing to use Pi auth path ${path} because its hard-link identity is unsafe.`);
1154
1113
  }
1155
1114
  }
1156
- async function writePiAuthStoreAtomically(path, auth, original, ownerUid, assertLockHeld, hooks) {
1115
+ async function writePiAuthStoreAtomically(path, auth, original, ownerUid, assertLockHeld, hooks, abortSignal, onCredentialStoreMutation) {
1116
+ throwIfProviderAuthAborted(abortSignal);
1157
1117
  await assertPiAuthStoreUnchanged(path, original, ownerUid);
1118
+ throwIfProviderAuthAborted(abortSignal);
1158
1119
  const dir = dirname(path);
1159
1120
  await mkdir(dir, { recursive: true, mode: 0o700 });
1121
+ throwIfProviderAuthAborted(abortSignal);
1160
1122
  const tempDir = await mkdtemp(join(dir, ".mono-agent-pi-auth-write-"));
1161
1123
  const tempPath = join(tempDir, "auth.json");
1162
1124
  let promotionInstalled = false;
1163
1125
  let operationError;
1164
1126
  try {
1127
+ throwIfProviderAuthAborted(abortSignal);
1165
1128
  await writeFile(tempPath, `${JSON.stringify(auth, null, 2)}\n`, { encoding: "utf8", flag: "wx", mode: 0o600 });
1129
+ throwIfProviderAuthAborted(abortSignal);
1166
1130
  await syncFile(tempPath);
1131
+ throwIfProviderAuthAborted(abortSignal);
1167
1132
  await assertPiAuthStoreUnchanged(path, original, ownerUid);
1168
- await promotePiAuthStoreWithoutClobber(tempPath, path, original, ownerUid, assertLockHeld, undefined, hooks);
1133
+ throwIfProviderAuthAborted(abortSignal);
1134
+ await promotePiAuthStoreWithoutClobber(tempPath, path, original, ownerUid, assertLockHeld, undefined, hooks, abortSignal, onCredentialStoreMutation);
1169
1135
  promotionInstalled = true;
1170
1136
  try {
1171
1137
  await hooks.beforePiAuthPostMutationSync?.(path);
@@ -1208,8 +1174,9 @@ function samePiAuthStoreSnapshot(left, right) {
1208
1174
  left.size === right.size &&
1209
1175
  left.contents === right.contents;
1210
1176
  }
1211
- async function promotePiAuthStoreWithoutClobber(stagedPath, targetPath, expected, ownerUid, assertLockHeld, intendedInput, hooks = {}) {
1177
+ async function promotePiAuthStoreWithoutClobber(stagedPath, targetPath, expected, ownerUid, assertLockHeld, intendedInput, hooks = {}, abortSignal, onCredentialStoreMutation) {
1212
1178
  const intended = intendedInput ?? await readPiAuthStore(stagedPath, piAuthSingleLinkPolicy(ownerUid));
1179
+ throwIfProviderAuthAborted(abortSignal);
1213
1180
  if (!intended.exists) {
1214
1181
  throw new Error(`Pi auth staging file ${stagedPath} disappeared before promotion.`);
1215
1182
  }
@@ -1218,10 +1185,14 @@ async function promotePiAuthStoreWithoutClobber(stagedPath, targetPath, expected
1218
1185
  try {
1219
1186
  await hooks.beforePiAuthPromotion?.(targetPath, stagedPath);
1220
1187
  await assertLockHeld();
1188
+ // This is the last safe cancellation point. Once target mutation starts,
1189
+ // the existing promotion/recovery transaction must run to completion.
1190
+ throwIfProviderAuthAborted(abortSignal);
1221
1191
  installed = await linkPiFileIfAbsent(stagedPath, targetPath);
1222
1192
  if (!installed) {
1223
1193
  throw new Error(`Pi auth file ${targetPath} changed during credential setup; the newer file was preserved.`);
1224
1194
  }
1195
+ onCredentialStoreMutation?.();
1225
1196
  await hooks.afterPiAuthLink?.(targetPath, stagedPath);
1226
1197
  await assertPromotedPiAuthStore(intended, stagedPath, targetPath, ownerUid);
1227
1198
  return;
@@ -1241,10 +1212,15 @@ async function promotePiAuthStoreWithoutClobber(stagedPath, targetPath, expected
1241
1212
  try {
1242
1213
  await hooks.beforePiAuthPromotion?.(targetPath, stagedPath);
1243
1214
  await assertLockHeld();
1215
+ // Abort cannot safely split the rename/install/recovery sequence below.
1216
+ throwIfProviderAuthAborted(abortSignal);
1244
1217
  try {
1245
1218
  await rename(targetPath, backupPath);
1246
1219
  backupCreated = true;
1247
1220
  targetMutationStarted = true;
1221
+ // Renaming the existing target is the first credential mutation, even
1222
+ // if a later validation fails and recovery restores that same inode.
1223
+ onCredentialStoreMutation?.();
1248
1224
  }
1249
1225
  catch (error) {
1250
1226
  if (error.code === "ENOENT") {