@x-otto/cli 0.0.1-alpha.16-debug → 0.0.1-alpha.17

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 (111) hide show
  1. package/README.md +65 -65
  2. package/dist/{auth-command-CKlvZtbJ.js → auth-command-kkJh-O5y.js} +2 -2
  3. package/dist/auth-command-kkJh-O5y.js.map +1 -0
  4. package/dist/build-id-B2hTdEbZ.js +3 -0
  5. package/dist/build-id-B2hTdEbZ.js.map +1 -0
  6. package/dist/bundled-extensions/plugin-otto-wire-protocols/plugin-dist/meta.json +1 -1
  7. package/dist/bundled-extensions/plugin-otto-wire-protocols/plugin-dist/plugin.cjs +37144 -193
  8. package/dist/bundled-extensions/plugin-otto-wire-protocols/src/anthropic-messages.ts +2 -2
  9. package/dist/bundled-extensions-C3n8jg20.js +3 -0
  10. package/dist/bundled-extensions-C3n8jg20.js.map +1 -0
  11. package/dist/{command-dispatcher-DibEV53Q.js → command-dispatcher-CbFjx7bg.js} +6 -6
  12. package/dist/command-dispatcher-CbFjx7bg.js.map +1 -0
  13. package/dist/{config-migration-DatflIxs.js → config-migration-0zdXsEDB.js} +1 -1
  14. package/dist/{config-migration-DatflIxs.js.map → config-migration-0zdXsEDB.js.map} +1 -1
  15. package/dist/create-host-app-BXQ8bU-B.js +3 -0
  16. package/dist/create-host-app-BXQ8bU-B.js.map +1 -0
  17. package/dist/create-host-app-DXII2WTM.js +2 -0
  18. package/dist/{daemon-COESl-zU.js → daemon-BtiaXSxn.js} +1 -1
  19. package/dist/{daemon-COESl-zU.js.map → daemon-BtiaXSxn.js.map} +1 -1
  20. package/dist/{daemon-base-YOWgYYN7.js → daemon-base-DKeB2Nyv.js} +1 -1
  21. package/dist/{daemon-base-YOWgYYN7.js.map → daemon-base-DKeB2Nyv.js.map} +1 -1
  22. package/dist/{debug-CiosFwme.js → debug-DfgcrVCI.js} +2 -2
  23. package/dist/{debug-CiosFwme.js.map → debug-DfgcrVCI.js.map} +1 -1
  24. package/dist/discover-with-bundled-B5d4q___.js +2 -0
  25. package/dist/discover-with-bundled-CF8qFP41.js +3 -0
  26. package/dist/discover-with-bundled-CF8qFP41.js.map +1 -0
  27. package/dist/doctor-DbQC8Z7p.js +36 -0
  28. package/dist/doctor-DbQC8Z7p.js.map +1 -0
  29. package/dist/{doctor-attach-_zeIJewx.js → doctor-attach-OJHn8L52.js} +2 -2
  30. package/dist/{doctor-attach-_zeIJewx.js.map → doctor-attach-OJHn8L52.js.map} +1 -1
  31. package/dist/{doctor-cdp-K_mIFRfA.js → doctor-cdp-D66ChCCN.js} +1 -1
  32. package/dist/{doctor-cdp-K_mIFRfA.js.map → doctor-cdp-D66ChCCN.js.map} +1 -1
  33. package/dist/{doctor-heap-Rr2nNvcw.js → doctor-heap-Brsro5QJ.js} +2 -2
  34. package/dist/{doctor-heap-Rr2nNvcw.js.map → doctor-heap-Brsro5QJ.js.map} +1 -1
  35. package/dist/{doctor-ps-OL3FGQYu.js → doctor-ps-B4Syy9qa.js} +2 -2
  36. package/dist/{doctor-ps-OL3FGQYu.js.map → doctor-ps-B4Syy9qa.js.map} +1 -1
  37. package/dist/{extension-DAex6RFK.js → extension-DLFCUBJr.js} +41 -33
  38. package/dist/extension-DLFCUBJr.js.map +1 -0
  39. package/dist/extension-I87MkZYp.js +2 -0
  40. package/dist/{extension-plugin-D7gnpllF.js → extension-plugin-DoEcnDu5.js} +4 -4
  41. package/dist/{extension-plugin-D7gnpllF.js.map → extension-plugin-DoEcnDu5.js.map} +1 -1
  42. package/dist/extension-plugin-VUdbaAN7.js +2 -0
  43. package/dist/feedback-DwQu2BmU.js +21 -0
  44. package/dist/feedback-DwQu2BmU.js.map +1 -0
  45. package/dist/feedback-j4tDn2uI.js +2 -0
  46. package/dist/{feishu-setup-DIcd3PMK.js → feishu-setup-C2UDdpIm.js} +2 -2
  47. package/dist/{feishu-setup-DIcd3PMK.js.map → feishu-setup-C2UDdpIm.js.map} +1 -1
  48. package/dist/ftue-doctor-recovery-DhiseXnP.js +3 -0
  49. package/dist/ftue-doctor-recovery-DhiseXnP.js.map +1 -0
  50. package/dist/index.d.ts.map +1 -1
  51. package/dist/index.js +10 -10
  52. package/dist/index.js.map +1 -1
  53. package/dist/install-DkJgbg2p.js +2 -0
  54. package/dist/{install-DlVJRHRT.js → install-hTDjeo61.js} +1 -1
  55. package/dist/{install-DlVJRHRT.js.map → install-hTDjeo61.js.map} +1 -1
  56. package/dist/{mcp-DbTYT7hB.js → mcp-BDfBf6gx.js} +1 -1
  57. package/dist/{mcp-DbTYT7hB.js.map → mcp-BDfBf6gx.js.map} +1 -1
  58. package/dist/{migrate-boDXhEyV.js → migrate-4QDwYLf6.js} +2 -2
  59. package/dist/{migrate-boDXhEyV.js.map → migrate-4QDwYLf6.js.map} +1 -1
  60. package/dist/{model-auth-Dih25xOB.js → model-auth-B6ufdM5K.js} +2 -2
  61. package/dist/{model-auth-Dih25xOB.js.map → model-auth-B6ufdM5K.js.map} +1 -1
  62. package/dist/model-auth-DMczbHA9.js +2 -0
  63. package/dist/{observe-CVg-MRM2.js → observe-C2jjDNDa.js} +2 -2
  64. package/dist/{observe-CVg-MRM2.js.map → observe-C2jjDNDa.js.map} +1 -1
  65. package/dist/{parse-cli-Dr-Fl0on.js → parse-cli-Cw5qyM5B.js} +2 -2
  66. package/dist/{parse-cli-Dr-Fl0on.js.map → parse-cli-Cw5qyM5B.js.map} +1 -1
  67. package/dist/{persistenced-CCwHu1Ww.js → persistenced-CcAhVOE7.js} +2 -2
  68. package/dist/{persistenced-CCwHu1Ww.js.map → persistenced-CcAhVOE7.js.map} +1 -1
  69. package/dist/plugin-assembly-check-CvuJ4dHf.js +3 -0
  70. package/dist/plugin-assembly-check-CvuJ4dHf.js.map +1 -0
  71. package/dist/{proxy-evg7ZvoD.js → proxy-CMQBvdZC.js} +1 -1
  72. package/dist/{proxy-evg7ZvoD.js.map → proxy-CMQBvdZC.js.map} +1 -1
  73. package/dist/proxy-TzOLqtkc.js +2 -0
  74. package/dist/{ps-DKrluEuy.js → ps-BWGntaR4.js} +1 -1
  75. package/dist/{ps-DKrluEuy.js.map → ps-BWGntaR4.js.map} +1 -1
  76. package/dist/{registry-D0NONjLv.js → registry-Cr5To_5r.js} +3 -3
  77. package/dist/registry-Cr5To_5r.js.map +1 -0
  78. package/dist/registry-DAJ7oZTe.js +2 -0
  79. package/dist/{remote-persistence-server-B_hONoVR.js → remote-persistence-server-CLI-y-zp.js} +2 -2
  80. package/dist/{remote-persistence-server-B_hONoVR.js.map → remote-persistence-server-CLI-y-zp.js.map} +1 -1
  81. package/dist/{run-attach-Ci5jYyCa.js → run-attach-DZmBqVjI.js} +2 -2
  82. package/dist/{run-attach-Ci5jYyCa.js.map → run-attach-DZmBqVjI.js.map} +1 -1
  83. package/dist/{serve-pVR6UIT9.js → serve-vWHGydiC.js} +3 -3
  84. package/dist/serve-vWHGydiC.js.map +1 -0
  85. package/dist/{service-client-BLNeugM9.js → service-client-Cr4sxDVM.js} +1 -1
  86. package/dist/{service-client-BLNeugM9.js.map → service-client-Cr4sxDVM.js.map} +1 -1
  87. package/dist/{time-travel-ZozuPPI-.js → time-travel-D1sg5dEb.js} +2 -2
  88. package/dist/{time-travel-ZozuPPI-.js.map → time-travel-D1sg5dEb.js.map} +1 -1
  89. package/dist/{version-Cd8HZ7ua.js → version-BaBgJOxV.js} +2 -2
  90. package/dist/{version-Cd8HZ7ua.js.map → version-BaBgJOxV.js.map} +1 -1
  91. package/package.json +3 -3
  92. package/dist/auth-command-CKlvZtbJ.js.map +0 -1
  93. package/dist/build-id-CIFJCmlj.js +0 -3
  94. package/dist/build-id-CIFJCmlj.js.map +0 -1
  95. package/dist/command-dispatcher-DibEV53Q.js.map +0 -1
  96. package/dist/discover-with-bundled-wSuXDvNc.js +0 -3
  97. package/dist/discover-with-bundled-wSuXDvNc.js.map +0 -1
  98. package/dist/doctor-C84-hhEr.js +0 -30
  99. package/dist/doctor-C84-hhEr.js.map +0 -1
  100. package/dist/extension-C3AP3KxC.js +0 -2
  101. package/dist/extension-DAex6RFK.js.map +0 -1
  102. package/dist/extension-plugin-fPDz7XlG.js +0 -2
  103. package/dist/feedback-BVl4sRah.js +0 -21
  104. package/dist/feedback-BVl4sRah.js.map +0 -1
  105. package/dist/feedback-DAY-1bJ0.js +0 -2
  106. package/dist/install-WCcQ9k9M.js +0 -2
  107. package/dist/model-auth-BxHBaDQx.js +0 -2
  108. package/dist/proxy-BvdBsB1O.js +0 -2
  109. package/dist/registry-B3nfN62q.js +0 -2
  110. package/dist/registry-D0NONjLv.js.map +0 -1
  111. package/dist/serve-pVR6UIT9.js.map +0 -1
package/README.md CHANGED
@@ -1,78 +1,78 @@
1
1
  # @x-otto/cli
2
2
 
3
- ## 模块定位
3
+ ## Module Purpose
4
4
 
5
- Otto 命令行入口,解析参数并分发到 Print / JSON / Interactive 运行模式与子命令。
5
+ Otto's command-line entry point — parses arguments and dispatches to Print / JSON / Interactive run modes and subcommands.
6
6
 
7
- ## 使用方式
7
+ ## Usage
8
8
 
9
9
  ```bash
10
- # Print 模式(单次执行)
10
+ # Print mode (single run)
11
11
  otto "fix the bug" -p
12
12
 
13
- # Interactive 模式(REPL,默认)
13
+ # Interactive mode (REPL, default)
14
14
  otto -i
15
15
 
16
- # JSON 模式
16
+ # JSON mode
17
17
  otto "summarize this file" --json
18
18
 
19
- # 指定模型
19
+ # Specify a model
20
20
  otto "explain this" -m claude-sonnet-4
21
21
 
22
- # 启用调试
22
+ # Enable debugging
23
23
  otto -i --inspect
24
24
 
25
- # 子命令
26
- otto doctor # 环境诊断
27
- otto config # 配置迁移
28
- otto auth # 认证管理
29
- otto extension # 插件管理(install / list / update / remove / trust
30
- otto serve # 启动 HTTP/WS service
31
- otto persistenced # 独立持久化存储服务
32
- otto observe # 观测面板
33
- otto debug # 调试面板
34
- otto time-travel # 时间旅行(checkpoints / restore / fork / replay
35
- otto mcp # MCP server OAuth 管理
36
- otto ps # 进程列表
37
- otto migrate # 数据/配置导入导出
38
- otto feedback # 反馈管理
25
+ # Subcommands
26
+ otto doctor # environment diagnostics
27
+ otto config # configuration migration
28
+ otto auth # credential management
29
+ otto extension # plugin management (install / list / update / remove / trust)
30
+ otto serve # start HTTP/WS service
31
+ otto persistenced # standalone persistence storage service
32
+ otto observe # observation panel
33
+ otto debug # debug panel
34
+ otto time-travel # time travel (checkpoints / restore / fork / replay)
35
+ otto mcp # MCP server OAuth management
36
+ otto ps # process list
37
+ otto migrate # data/config import & export
38
+ otto feedback # feedback management
39
39
  ```
40
40
 
41
- ## 参数
41
+ ## Arguments
42
42
 
43
- | 参数 | 说明 |
43
+ | Argument | Description |
44
44
  |------|------|
45
- | `-p` / `--print` | Print 模式 |
46
- | `-i` / `--interactive` | Interactive 模式 |
47
- | `--json` | JSON 模式 |
48
- | `-m` / `--model` | 指定模型 |
49
- | `-c` / `--config` | 配置文件路径 |
50
- | `-d` / `--project` | 工作目录 |
51
- | `-v` / `--verbose` | 详细日志 |
52
- | `-q` / `--quiet` | error 日志 |
53
- | `--continue` | 继续上次会话 |
54
- | `--inspect[=port]` | 启用调试(默认 9229 |
55
- | `--max-tool-turns` | 单回合最大工具调用数 |
56
- | `--max-tool-turn-extensions` | 触顶后压缩续跑扩展次数 |
57
- | `--session-url` | 远程持久化 URL |
58
- | `--session-token` | 远程持久化 Bearer token |
59
- | `--id` | 显式 workspace ID |
60
- | `--help` / `--version` | 帮助 / 版本 |
61
-
62
- ## 安装
45
+ | `-p` / `--print` | Print mode |
46
+ | `-i` / `--interactive` | Interactive mode |
47
+ | `--json` | JSON mode |
48
+ | `-m` / `--model` | Specify model |
49
+ | `-c` / `--config` | Config file path |
50
+ | `-d` / `--project` | Working directory |
51
+ | `-v` / `--verbose` | Verbose logging |
52
+ | `-q` / `--quiet` | Error-level logging only |
53
+ | `--continue` | Resume last session |
54
+ | `--inspect[=port]` | Enable debugging (default 9229) |
55
+ | `--max-tool-turns` | Max tool calls per turn |
56
+ | `--max-tool-turn-extensions` | Number of compaction-and-continue extensions after hitting the cap |
57
+ | `--session-url` | Remote persistence URL |
58
+ | `--session-token` | Remote persistence bearer token |
59
+ | `--id` | Explicit workspace ID |
60
+ | `--help` / `--version` | Help / version |
61
+
62
+ ## Installation
63
63
 
64
64
  ```bash
65
65
  pnpm add @x-otto/cli
66
66
  ```
67
67
 
68
- 或从仓库构建:
68
+ Or build from the repo:
69
69
 
70
70
  ```bash
71
71
  pnpm --filter @x-otto/cli build
72
72
  node packages/cli/bin/otto.js
73
73
  ```
74
74
 
75
- 全局安装(dev):
75
+ Global install (dev):
76
76
 
77
77
  ```bash
78
78
  pnpm --filter @x-otto/cli build
@@ -81,30 +81,30 @@ pnpm --global link packages/cli
81
81
 
82
82
  ## API
83
83
 
84
- | 导出 | 类型 | 说明 |
84
+ | Export | Type | Description |
85
85
  |---|---|---|
86
- | `runCli` | `() => Promise<number>` | 主执行入口,返回退出码 |
86
+ | `runCli` | `() => Promise<number>` | Main execution entry point, returns exit code |
87
87
 
88
- ## 目录概览
88
+ ## Directory Overview
89
89
 
90
90
  ```
91
91
  bin/
92
- otto # 二进制入口(#!/usr/bin/env node
92
+ otto # binary entry point (#!/usr/bin/env node)
93
93
  src/
94
- cli.ts # 主执行入口(SUB_COMMANDS 注册表)
95
- parse-cli.ts # 参数解析(parseCLI
96
- types.ts # 核心类型
97
- index.ts # 顶层执行 + runCli 导出
98
- auth-command.ts # auth 子命令
99
- build-id.ts # 构建元信息
100
- commands/ # 子命令模块(~49 文件)
101
- i18n/ # 国际化类型
102
- modes/ # 运行模式辅助
103
- session-contract/ # 会话契约
104
- tests/ # 14 个测试文件
94
+ cli.ts # main execution entry (SUB_COMMANDS registry)
95
+ parse-cli.ts # argument parsing (parseCLI)
96
+ types.ts # core types
97
+ index.ts # top-level execution + runCli export
98
+ auth-command.ts # auth subcommand
99
+ build-id.ts # build metadata
100
+ commands/ # subcommand modules (~49 files)
101
+ i18n/ # internationalization types
102
+ modes/ # run-mode helpers
103
+ session-contract/ # session contract
104
+ tests/ # 14 test files
105
105
  ```
106
106
 
107
- ## 开发命令
107
+ ## Development Commands
108
108
 
109
109
  ```bash
110
110
  pnpm --filter @x-otto/cli build
@@ -112,9 +112,9 @@ pnpm --filter @x-otto/cli typecheck
112
112
  pnpm --filter @x-otto/cli clean
113
113
  ```
114
114
 
115
- ## 关联包
115
+ ## Related Packages
116
116
 
117
- `@x-otto/agent`、`@x-otto/ai`、`@x-otto/coding`、`@x-otto/env`、`@x-otto/hooks`、`@x-otto/mcp`、
118
- `@x-otto/memory`、`@x-otto/persistence`、`@x-otto/interchange`、`@x-otto/remote-persistence-server`、
119
- `@x-otto/runtime`、`@x-otto/schedule`、`@x-otto/service`、`@x-otto/session`、`@x-otto/session-contract`、
120
- `@x-otto/setting`、`@x-otto/shared`、`@x-otto/tools`、`@x-otto/trace-view`、`@x-otto/tui`
117
+ `@x-otto/agent`, `@x-otto/ai`, `@x-otto/coding`, `@x-otto/env`, `@x-otto/hooks`, `@x-otto/mcp`,
118
+ `@x-otto/memory`, `@x-otto/persistence`, `@x-otto/interchange`, `@x-otto/remote-persistence-server`,
119
+ `@x-otto/runtime`, `@x-otto/schedule`, `@x-otto/service`, `@x-otto/session`, `@x-otto/session-contract`,
120
+ `@x-otto/setting`, `@x-otto/shared`, `@x-otto/tools`, `@x-otto/trace-view`, `@x-otto/tui`
@@ -1,5 +1,5 @@
1
1
  #!/usr/bin/env node
2
- import{createApp as e}from"@x-otto/coding";import{createDefaultAuthStore as t}from"@x-otto/ai";import{createInterface as n}from"node:readline/promises";async function r(n,i={}){if(!i.authStore&&i.bootstrap){let t=e({workspaceDir:i.bootstrap.workspaceDir,projectConfigPath:i.bootstrap.projectConfigPath,logger:{name:`otto-auth`,level:i.bootstrap.verbose?`debug`:`info`,destination:`stderr`}});try{return await t.start(),await r(n,{...i,authStore:t.authStore,bootstrap:void 0})}finally{await t.stop()}}let s=i.stdout??(e=>process.stdout.write(e)),l=i.stderr??(e=>process.stderr.write(e)),u=i.authStore??t({watchForExternalChanges:!1}),[d,f]=n;switch(d){case`login`:return a(u,f,{stdout:s,stderr:l,prompt:i.prompt});case`logout`:return o(u,f,{stdout:s,stderr:l});case`status`:case void 0:return c(u,{stdout:s});default:return l(`otto auth: unknown action '${d}'. Use login | status | logout.\n`),1}}function i(e){return e.oauth.list().map(e=>e.id)}async function a(e,t,r){let a=i(e);if(a.length===0)return r.stderr(`otto auth login: no OAuth-capable providers available yet.
2
+ import{t as e}from"./create-host-app-BXQ8bU-B.js";import{createDefaultAuthStore as t}from"@x-otto/ai";import{createInterface as n}from"node:readline/promises";async function r(n,i={}){if(!i.authStore&&i.bootstrap){let t=e({workspaceDir:i.bootstrap.workspaceDir,projectConfigPath:i.bootstrap.projectConfigPath,logger:{name:`otto-auth`,level:i.bootstrap.verbose?`debug`:`info`,destination:`stderr`}});try{return await t.start(),await r(n,{...i,authStore:t.authStore,bootstrap:void 0})}finally{await t.stop()}}let s=i.stdout??(e=>process.stdout.write(e)),l=i.stderr??(e=>process.stderr.write(e)),u=i.authStore??t({watchForExternalChanges:!1}),[d,f]=n;switch(d){case`login`:return a(u,f,{stdout:s,stderr:l,prompt:i.prompt});case`logout`:return o(u,f,{stdout:s,stderr:l});case`status`:case void 0:return c(u,{stdout:s});default:return l(`otto auth: unknown action '${d}'. Use login | status | logout.\n`),1}}function i(e){return e.oauth.list().map(e=>e.id)}async function a(e,t,r){let a=i(e);if(a.length===0)return r.stderr(`otto auth login: no OAuth-capable providers available yet.
3
3
  Install a provider plugin first — run \`otto\` (interactive) for guided setup,
4
4
  or: otto extension install anthropic-provider
5
5
  `),1;if(!t)return r.stderr(`otto auth login: missing provider. One of: ${a.join(`, `)}\n`),1;let o=e.oauth.get(t);if(!o)return r.stderr(`otto auth login: unknown provider '${t}'. One of: ${a.join(`, `)}\n`),r.stderr(`Hint: plugin providers (cursor, anthropic, …) need the plugin installed with provider capability granted.
@@ -8,4 +8,4 @@ or: otto extension install anthropic-provider
8
8
  `),1;let s=r.prompt?void 0:n({input:process.stdin,output:process.stdout}),c=r.prompt??(e=>s.question(e)),l=new AbortController,u=()=>l.abort();process.on(`SIGINT`,u);try{let n={onAuth:e=>{r.stdout(`\nOpen this URL in your browser to authorize:\n ${e.url}\n`),e.code&&r.stdout(`Code: ${e.code}\n`),e.instructions&&r.stdout(`${e.instructions}\n`)},onPrompt:async e=>{let t=e.placeholder?` (${e.placeholder})`:``;return(await c(`${e.message}${t}: `)).trim()},onManualCode:async e=>{let t=c(`
9
9
  Paste the code here: `).then(e=>e.trim(),()=>``);return e?e.aborted?``:Promise.race([t,new Promise(t=>{e.addEventListener(`abort`,()=>t(``),{once:!0})})]):t},onProgress:e=>r.stdout(`${e}\n`),signal:l.signal};return await e.login(t,n),r.stdout(`\n✓ Logged in to ${o.name}.\n`),0}catch(e){return r.stderr(`\notto auth login failed: ${e.message}\n`),1}finally{process.off(`SIGINT`,u),s?.close()}}async function o(e,t,n){if(!t)return n.stderr(`otto auth logout: missing provider. One of: ${e.listProviders().join(`, `)}\n`),1;let r=await e.hasCredential(t);return await e.logout(t),n.stdout(r?`✓ Logged out of ${t}.\n`:`${t} was not logged in.\n`),0}const s={oauth:`OAuth`,api_key:`API key (stored)`,env:`API key (env)`};async function c(e,t){await e.ensureInitialized(),t.stdout(`Authentication status:
10
10
  `);for(let n of e.listProviders()){let r=await e.getAuthSource(n),i=r?s[r]:`not configured`;t.stdout(` ${n.padEnd(16)} ${i}\n`)}return 0}export{r as runAuthCommand};
11
- //# sourceMappingURL=auth-command-CKlvZtbJ.js.map
11
+ //# sourceMappingURL=auth-command-kkJh-O5y.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"auth-command-kkJh-O5y.js","names":[],"sources":["../src/auth-command.ts"],"sourcesContent":["import { createInterface } from 'node:readline/promises'\n\nimport { createHostApp } from './create-host-app'\nimport { createDefaultAuthStore } from '@x-otto/ai'\nimport type { AuthStore, OAuthLoginOptions } from '@x-otto/ai'\n\n/**\n * `otto auth login|status|logout` 子命令(M8-07)。\n *\n * 驱动 AuthStore.login 的 onAuth/onPrompt/onManualCode 回调:\n * - Anthropic(usesCallbackServer=false)→ loopback(54545) 优先自动回填,\n * 端口占用时回退托管回调 + 用户回贴 code(onManualCode 必须提供);\n * - loopback provider(OpenAI/Codex,usesCallbackServer=true)→ 浏览器重定向自动完成。\n * - 插件 OAuth(cursor/anthropic 等)→ 须 bootstrap App 装载插件后再查 oauth 表(RFC-130 M131-1)。\n */\nexport interface AuthBootstrapOptions {\n workspaceDir: string\n projectConfigPath?: string\n verbose?: boolean\n}\n\nexport interface AuthCommandDeps {\n authStore?: AuthStore\n /** 未注入 authStore 时,经 App.start() 装载插件 OAuth(对齐 TUI `/auth`)。 */\n bootstrap?: AuthBootstrapOptions\n stdout?: (s: string) => void\n stderr?: (s: string) => void\n /** 单行读取器(注入便于测试);未提供时按需创建 readline。 */\n prompt?: (question: string) => Promise<string>\n}\n\nexport async function runAuthCommand(args: string[], deps: AuthCommandDeps = {}): Promise<number> {\n if (!deps.authStore && deps.bootstrap) {\n const app = createHostApp({\n workspaceDir: deps.bootstrap.workspaceDir,\n projectConfigPath: deps.bootstrap.projectConfigPath,\n logger: {\n name: 'otto-auth',\n level: deps.bootstrap.verbose ? 'debug' : 'info',\n destination: 'stderr',\n },\n })\n try {\n await app.start()\n return await runAuthCommand(args, {\n ...deps,\n authStore: app.authStore,\n bootstrap: undefined,\n })\n } finally {\n await app.stop()\n }\n }\n\n const stdout = deps.stdout ?? ((s) => process.stdout.write(s))\n const stderr = deps.stderr ?? ((s) => process.stderr.write(s))\n // watchForExternalChanges:false —— `otto auth *` 是一次性命令,跑完即退出,不需要跨进程凭据\n // 实时同步(那是给 TUI/serve 长驻进程用的)。AuthStore 的 fs.watch 句柄本身已 unref(不阻塞\n // 事件循环清空,见 auth-store.ts setupWatcher 注释),此处显式关闭仍是更准确的语义表达——\n // 避免为一个秒退的脚本无谓建立/拆除一个不会被用到的 watcher。\n const authStore = deps.authStore ?? createDefaultAuthStore({ watchForExternalChanges: false })\n\n const [action, provider] = args\n\n switch (action) {\n case 'login':\n return authLogin(authStore, provider, { stdout, stderr, prompt: deps.prompt })\n case 'logout':\n return authLogout(authStore, provider, { stdout, stderr })\n case 'status':\n case undefined:\n return authStatus(authStore, { stdout })\n default:\n stderr(`otto auth: unknown action '${action}'. Use login | status | logout.\\n`)\n return 1\n }\n}\n\nfunction loginableProviders(authStore: AuthStore): string[] {\n return authStore.oauth.list().map((p) => p.id)\n}\n\nasync function authLogin(\n authStore: AuthStore,\n provider: string | undefined,\n io: { stdout: (s: string) => void; stderr: (s: string) => void; prompt?: (q: string) => Promise<string> },\n): Promise<number> {\n const providers = loginableProviders(authStore)\n // UX(round 6):零 provider 插件时 providers 为空数组——\"One of: \"后面是空串,\n // 用户面对死端。指回引导路径而不是展示空名单。\n if (providers.length === 0) {\n io.stderr(\n 'otto auth login: no OAuth-capable providers available yet.\\n' +\n 'Install a provider plugin first — run `otto` (interactive) for guided setup,\\n' +\n 'or: otto extension install anthropic-provider\\n',\n )\n return 1\n }\n if (!provider) {\n io.stderr(`otto auth login: missing provider. One of: ${providers.join(', ')}\\n`)\n return 1\n }\n\n const oauth = authStore.oauth.get(provider)\n if (!oauth) {\n io.stderr(`otto auth login: unknown provider '${provider}'. One of: ${providers.join(', ')}\\n`)\n io.stderr(\n 'Hint: plugin providers (cursor, anthropic, …) need the plugin installed with provider capability granted.\\n' +\n ' otto extension install --link extensions/plugin-cursor --yes\\n' +\n ' # user-scope install auto-trusts; then otto auth login cursor\\n',\n )\n return 1\n }\n\n const rl = io.prompt ? undefined : createInterface({ input: process.stdin, output: process.stdout })\n const ask = io.prompt ?? ((q: string) => rl!.question(q))\n\n const controller = new AbortController()\n const onSigint = (): void => controller.abort()\n process.on('SIGINT', onSigint)\n\n try {\n const options: OAuthLoginOptions = {\n onAuth: (info) => {\n io.stdout(`\\nOpen this URL in your browser to authorize:\\n ${info.url}\\n`)\n if (info.code) {\n io.stdout(`Code: ${info.code}\\n`)\n }\n if (info.instructions) {\n io.stdout(`${info.instructions}\\n`)\n }\n },\n onPrompt: async (p) => {\n const suffix = p.placeholder ? ` (${p.placeholder})` : ''\n return (await ask(`${p.message}${suffix}: `)).trim()\n },\n // loopback 回调先完成时经 signal 放行。readline 本身无法中断,由 finally 的\n // rl.close() 收尾——close 会 reject 悬挂的 question,故 catch 归一为空串防 unhandled。\n onManualCode: async (signal?: AbortSignal) => {\n const question = ask('\\nPaste the code here: ').then(\n (s) => s.trim(),\n () => '',\n )\n if (!signal) return question\n if (signal.aborted) return ''\n return Promise.race([\n question,\n new Promise<string>((resolve) => {\n signal.addEventListener('abort', () => resolve(''), { once: true })\n }),\n ])\n },\n onProgress: (m) => io.stdout(`${m}\\n`),\n signal: controller.signal,\n }\n\n await authStore.login(provider, options)\n io.stdout(`\\n✓ Logged in to ${oauth.name}.\\n`)\n return 0\n } catch (error) {\n io.stderr(`\\notto auth login failed: ${(error as Error).message}\\n`)\n return 1\n } finally {\n process.off('SIGINT', onSigint)\n rl?.close()\n }\n}\n\nasync function authLogout(\n authStore: AuthStore,\n provider: string | undefined,\n io: { stdout: (s: string) => void; stderr: (s: string) => void },\n): Promise<number> {\n if (!provider) {\n io.stderr(\n `otto auth logout: missing provider. One of: ${authStore.listProviders().join(', ')}\\n`,\n )\n return 1\n }\n\n const had = await authStore.hasCredential(provider)\n await authStore.logout(provider)\n io.stdout(had ? `✓ Logged out of ${provider}.\\n` : `${provider} was not logged in.\\n`)\n return 0\n}\n\nconst SOURCE_LABEL: Record<string, string> = {\n oauth: 'OAuth',\n api_key: 'API key (stored)',\n env: 'API key (env)',\n}\n\nasync function authStatus(\n authStore: AuthStore,\n io: { stdout: (s: string) => void },\n): Promise<number> {\n // RFC-341 修复:`AuthStore.listProviders()` 是同步方法,读的是内存 cache——\n // cache 由 `ensureInitialized()`(异步读盘)填充,且没有任何调用方保证在\n // `listProviders()` 之前完成过初始化(`getAuthSource()` 等其余方法内部各自会\n // `await ensureInitialized()`,唯独 `listProviders()` 没有)。此前这里直接调\n // `listProviders()` 时 cache 大概率还是空的(首次调用、无其余方法先触发过初始化\n // 的一次性命令场景),导致 `otto auth status`/Setup Wizard 装完 provider 后\n // 立即查询状态永远显示\"未配置\"——即便凭据其实已经成功落盘(真实事故:OrbStack\n // 虚拟机全流程测试实测复现,auth.json 里确有凭据但 status/doctor 均报未配置)。\n await authStore.ensureInitialized()\n io.stdout('Authentication status:\\n')\n for (const provider of authStore.listProviders()) {\n const source = await authStore.getAuthSource(provider)\n const label = source ? SOURCE_LABEL[source] : 'not configured'\n io.stdout(` ${provider.padEnd(16)} ${label}\\n`)\n }\n return 0\n}\n"],"mappings":";+JA+BA,eAAsB,EAAe,EAAgB,EAAwB,EAAE,CAAmB,CAChG,GAAI,CAAC,EAAK,WAAa,EAAK,UAAW,CACrC,IAAM,EAAM,EAAc,CACxB,aAAc,EAAK,UAAU,aAC7B,kBAAmB,EAAK,UAAU,kBAClC,OAAQ,CACN,KAAM,YACN,MAAO,EAAK,UAAU,QAAU,QAAU,OAC1C,YAAa,SACd,CACF,CAAC,CACF,GAAI,CAEF,OADA,MAAM,EAAI,OAAO,CACV,MAAM,EAAe,EAAM,CAChC,GAAG,EACH,UAAW,EAAI,UACf,UAAW,IAAA,GACZ,CAAC,QACM,CACR,MAAM,EAAI,MAAM,EAIpB,IAAM,EAAS,EAAK,SAAY,GAAM,QAAQ,OAAO,MAAM,EAAE,EACvD,EAAS,EAAK,SAAY,GAAM,QAAQ,OAAO,MAAM,EAAE,EAKvD,EAAY,EAAK,WAAa,EAAuB,CAAE,wBAAyB,GAAO,CAAC,CAExF,CAAC,EAAQ,GAAY,EAE3B,OAAQ,EAAR,CACE,IAAK,QACH,OAAO,EAAU,EAAW,EAAU,CAAE,SAAQ,SAAQ,OAAQ,EAAK,OAAQ,CAAC,CAChF,IAAK,SACH,OAAO,EAAW,EAAW,EAAU,CAAE,SAAQ,SAAQ,CAAC,CAC5D,IAAK,SACL,KAAK,IAAA,GACH,OAAO,EAAW,EAAW,CAAE,SAAQ,CAAC,CAC1C,QAEE,OADA,EAAO,8BAA8B,EAAO,mCAAmC,CACxE,GAIb,SAAS,EAAmB,EAAgC,CAC1D,OAAO,EAAU,MAAM,MAAM,CAAC,IAAK,GAAM,EAAE,GAAG,CAGhD,eAAe,EACb,EACA,EACA,EACiB,CACjB,IAAM,EAAY,EAAmB,EAAU,CAG/C,GAAI,EAAU,SAAW,EAMvB,OALA,EAAG,OACD;;;EAGD,CACM,EAET,GAAI,CAAC,EAEH,OADA,EAAG,OAAO,8CAA8C,EAAU,KAAK,KAAK,CAAC,IAAI,CAC1E,EAGT,IAAM,EAAQ,EAAU,MAAM,IAAI,EAAS,CAC3C,GAAI,CAAC,EAOH,OANA,EAAG,OAAO,sCAAsC,EAAS,aAAa,EAAU,KAAK,KAAK,CAAC,IAAI,CAC/F,EAAG,OACD;;;EAGD,CACM,EAGT,IAAM,EAAK,EAAG,OAAS,IAAA,GAAY,EAAgB,CAAE,MAAO,QAAQ,MAAO,OAAQ,QAAQ,OAAQ,CAAC,CAC9F,EAAM,EAAG,SAAY,GAAc,EAAI,SAAS,EAAE,EAElD,EAAa,IAAI,gBACjB,MAAuB,EAAW,OAAO,CAC/C,QAAQ,GAAG,SAAU,EAAS,CAE9B,GAAI,CACF,IAAM,EAA6B,CACjC,OAAS,GAAS,CAChB,EAAG,OAAO,oDAAoD,EAAK,IAAI,IAAI,CACvE,EAAK,MACP,EAAG,OAAO,SAAS,EAAK,KAAK,IAAI,CAE/B,EAAK,cACP,EAAG,OAAO,GAAG,EAAK,aAAa,IAAI,EAGvC,SAAU,KAAO,IAAM,CACrB,IAAM,EAAS,EAAE,YAAc,KAAK,EAAE,YAAY,GAAK,GACvD,OAAQ,MAAM,EAAI,GAAG,EAAE,UAAU,EAAO,IAAI,EAAE,MAAM,EAItD,aAAc,KAAO,IAAyB,CAC5C,IAAM,EAAW,EAAI;uBAA0B,CAAC,KAC7C,GAAM,EAAE,MAAM,KACT,GACP,CAGD,OAFK,EACD,EAAO,QAAgB,GACpB,QAAQ,KAAK,CAClB,EACA,IAAI,QAAiB,GAAY,CAC/B,EAAO,iBAAiB,YAAe,EAAQ,GAAG,CAAE,CAAE,KAAM,GAAM,CAAC,EACnE,CACH,CAAC,CAPkB,GAStB,WAAa,GAAM,EAAG,OAAO,GAAG,EAAE,IAAI,CACtC,OAAQ,EAAW,OACpB,CAID,OAFA,MAAM,EAAU,MAAM,EAAU,EAAQ,CACxC,EAAG,OAAO,oBAAoB,EAAM,KAAK,KAAK,CACvC,QACA,EAAO,CAEd,OADA,EAAG,OAAO,6BAA8B,EAAgB,QAAQ,IAAI,CAC7D,SACC,CACR,QAAQ,IAAI,SAAU,EAAS,CAC/B,GAAI,OAAO,EAIf,eAAe,EACb,EACA,EACA,EACiB,CACjB,GAAI,CAAC,EAIH,OAHA,EAAG,OACD,+CAA+C,EAAU,eAAe,CAAC,KAAK,KAAK,CAAC,IACrF,CACM,EAGT,IAAM,EAAM,MAAM,EAAU,cAAc,EAAS,CAGnD,OAFA,MAAM,EAAU,OAAO,EAAS,CAChC,EAAG,OAAO,EAAM,mBAAmB,EAAS,KAAO,GAAG,EAAS,uBAAuB,CAC/E,EAGT,MAAM,EAAuC,CAC3C,MAAO,QACP,QAAS,mBACT,IAAK,gBACN,CAED,eAAe,EACb,EACA,EACiB,CASjB,MAAM,EAAU,mBAAmB,CACnC,EAAG,OAAO;EAA2B,CACrC,IAAK,IAAM,KAAY,EAAU,eAAe,CAAE,CAChD,IAAM,EAAS,MAAM,EAAU,cAAc,EAAS,CAChD,EAAQ,EAAS,EAAa,GAAU,iBAC9C,EAAG,OAAO,KAAK,EAAS,OAAO,GAAG,CAAC,GAAG,EAAM,IAAI,CAElD,MAAO"}
@@ -0,0 +1,3 @@
1
+ #!/usr/bin/env node
2
+ const e=4689,t=`83445bac7`;export{e as n,t};
3
+ //# sourceMappingURL=build-id-B2hTdEbZ.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"build-id-B2hTdEbZ.js","names":[],"sources":["../src/build-id.ts"],"sourcesContent":["// auto-generated by scripts/gen-build-id.mjs — DO NOT EDIT\nexport const BUILD_ID = 4689\nexport const BUILD_BRANCH = 'dev'\nexport const BUILD_HASH = '83445bac7'\n"],"mappings":";AACA,MAAa,EAAW,KAEX,EAAa"}
@@ -1 +1 @@
1
- {"apiVersion":1,"compilerVersion":"0.1.0-alpha.3","sourceHash":"751b68806b51427abf0408f41b78808a83834412f82502bb918d492e4cd44b57"}
1
+ {"apiVersion":1,"compilerVersion":"0.1.0-alpha.3","sourceHash":"831e810b41c3acebde9f13d0dd7806e131e5416a6e5839634af534ace7f0a693"}