@bolloon/bolloon-agent 0.3.51 → 0.4.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 (218) hide show
  1. package/README.md +135 -135
  2. package/bin/bolloon-cli.cjs +183 -183
  3. package/bin/bolloon.cjs +0 -0
  4. package/bin/bolloon.js +157 -0
  5. package/dist/agents/constraint-layer.js +19 -19
  6. package/dist/agents/judgment-protocol.js +14 -14
  7. package/dist/agents/loop-review.js +21 -0
  8. package/dist/agents/pi-sdk-tools.js +86 -2
  9. package/dist/agents/pi-sdk-types.js +12 -12
  10. package/dist/agents/pi-sdk.js +90 -90
  11. package/dist/agents/shell-guard.js +22 -1
  12. package/dist/agents/skill-organizer.js +19 -19
  13. package/dist/agents/verify-recipe.js +84 -0
  14. package/dist/agents/workflow-pivot-loop.js +101 -13
  15. package/dist/bollharness/src/scripts/deploy-guard.js +8 -8
  16. package/dist/bollharness-integration/context-router-judgment.js +4 -4
  17. package/dist/bollharness-integration/context-router.js +292 -292
  18. package/dist/bollharness-integration/gate-state-machine.js +13 -13
  19. package/dist/bollharness-integration/llm-judgment-engine.js +134 -134
  20. package/dist/bollharness-integration/skill-adapter.js +21 -21
  21. package/dist/bootstrap/chat-archiver.js +14 -14
  22. package/dist/bootstrap/context-os.js +50 -40
  23. package/dist/bootstrap/memory-compressor.js +13 -13
  24. package/dist/cli-entry.js +36 -36
  25. package/dist/context-compaction/auto-compact.js +7 -7
  26. package/dist/electron/first-run.js +54 -54
  27. package/dist/electron-build/electron/first-run.js +54 -54
  28. package/dist/electron-preload.js.map +1 -1
  29. package/dist/electron.js.map +1 -1
  30. package/dist/external-engines/delegate-handle.js +70 -0
  31. package/dist/external-engines/delegate.js +24 -3
  32. package/dist/index.js +112 -112
  33. package/dist/llm/error-lessons.js +53 -0
  34. package/dist/llm/llm-judgment-client.js +102 -102
  35. package/dist/llm/pi-ai.js +61 -48
  36. package/dist/llm/system-prompt/layers/channel/human-async.md +41 -41
  37. package/dist/llm/system-prompt/layers/channel/local.md +14 -14
  38. package/dist/llm/system-prompt/layers/channel/p2p-agent.md +18 -18
  39. package/dist/llm/system-prompt/layers/channel/p2p-peer-sync.md +51 -51
  40. package/dist/llm/system-prompt/layers/channel/p2p-proactive.md +43 -43
  41. package/dist/llm/system-prompt/layers/channel/p2p-visitor.md +19 -19
  42. package/dist/llm/system-prompt/layers/channel/session-handoff.md +61 -61
  43. package/dist/llm/system-prompt/layers/core/artifacts_storage.md +89 -89
  44. package/dist/llm/system-prompt/layers/core/evenhandedness.md +21 -21
  45. package/dist/llm/system-prompt/layers/core/external-engagement.md +73 -73
  46. package/dist/llm/system-prompt/layers/core/hibs_reminders.md +15 -15
  47. package/dist/llm/system-prompt/layers/core/identity.md +48 -48
  48. package/dist/llm/system-prompt/layers/core/knowledge.md +17 -17
  49. package/dist/llm/system-prompt/layers/core/memory_system.md +12 -12
  50. package/dist/llm/system-prompt/layers/core/network_filesystem.md +28 -28
  51. package/dist/llm/system-prompt/layers/core/refusal.md +37 -37
  52. package/dist/llm/system-prompt/layers/core/tone.md +31 -31
  53. package/dist/llm/system-prompt/layers/core/tools.thin.md +13 -13
  54. package/dist/llm/system-prompt/layers/core/wellbeing.md +41 -41
  55. package/dist/llm/system-prompt/layers/role/architect.md +20 -20
  56. package/dist/llm/system-prompt/layers/role/expert.md +19 -19
  57. package/dist/llm/system-prompt/layers/role/implementer.md +15 -15
  58. package/dist/llm/system-prompt/layers/role/security.md +15 -15
  59. package/dist/llm/system-prompt/layers/tool/artifacts.md +72 -72
  60. package/dist/llm/system-prompt/layers/tool/bash.md +25 -25
  61. package/dist/llm/system-prompt/layers/tool/goal_handoff.md +77 -77
  62. package/dist/llm/system-prompt/layers/tool/hibs_api.md +171 -171
  63. package/dist/llm/system-prompt/layers/tool/image_search.md +70 -70
  64. package/dist/llm/system-prompt/layers/tool/manifest.md +89 -89
  65. package/dist/llm/system-prompt/layers/tool/mcp_apps.md +53 -53
  66. package/dist/llm/system-prompt/layers/tool/p2p_request.md +61 -61
  67. package/dist/llm/system-prompt/layers/tool/web_search.md +83 -83
  68. package/dist/llm/system-prompt/registry.js +9 -1
  69. package/dist/llm/tool-manifest/ask_user_input.js +1 -1
  70. package/dist/llm/tool-manifest/bash.js +3 -3
  71. package/dist/llm/tool-manifest/create_file.js +4 -4
  72. package/dist/llm/tool-manifest/fetch_sports_data.js +3 -3
  73. package/dist/llm/tool-manifest/image_search.js +2 -2
  74. package/dist/llm/tool-manifest/index.js +0 -59
  75. package/dist/llm/tool-manifest/mcp.js +2 -2
  76. package/dist/llm/tool-manifest/message_compose.js +3 -3
  77. package/dist/llm/tool-manifest/places.js +2 -2
  78. package/dist/llm/tool-manifest/present_files.js +1 -1
  79. package/dist/llm/tool-manifest/recipe.js +2 -2
  80. package/dist/llm/tool-manifest/str_replace.js +5 -5
  81. package/dist/llm/tool-manifest/view.js +3 -3
  82. package/dist/llm/tool-manifest/weather.js +4 -4
  83. package/dist/llm/tool-manifest/web.js +4 -4
  84. package/dist/locales/en.js +28 -0
  85. package/dist/locales/zh.js +26 -0
  86. package/dist/pi-ecosystem-colony/index.js +365 -0
  87. package/dist/pi-ecosystem-judgment/causal-judge.js +51 -51
  88. package/dist/pi-ecosystem-judgment/distill-prompt.js +42 -42
  89. package/dist/pi-ecosystem-judgment/distillation.js +14 -14
  90. package/dist/pi-ecosystem-judgment/monitor-gate.js +28 -28
  91. package/dist/pi-ecosystem-judgment/value-injection.js +102 -102
  92. package/dist/security/context-router-tool.js +15 -15
  93. package/dist/social/ant-colony/AdaptiveHeartbeat.js +101 -0
  94. package/dist/social/ant-colony/PheromoneEngine.js +227 -0
  95. package/dist/social/ant-colony/index.js +6 -0
  96. package/dist/social/ant-colony/types.js +24 -0
  97. package/dist/storage/trajectory.js +101 -0
  98. package/dist/test/ai-judgment-test.js +80 -0
  99. package/dist/test/bollharness-integration.test.js +318 -0
  100. package/dist/test/channel-agent-multi-dialogue.js +205 -0
  101. package/dist/test/channel-heartbeat-agent-test.js +201 -0
  102. package/dist/test/constraint-layer.test.js +164 -0
  103. package/dist/test/diap-identity-test.js +172 -0
  104. package/dist/test/diap-quick-test.js +62 -0
  105. package/dist/test/global-shared-context.test.js +315 -0
  106. package/dist/test/harness-judgment-injection.test.js +246 -0
  107. package/dist/test/harness-workflow-integrator-test.js +228 -0
  108. package/dist/test/human-value-store.test.js +243 -0
  109. package/dist/test/hybrid-integration-test.js +118 -0
  110. package/dist/test/hybrid-messenger-verify.js +55 -0
  111. package/dist/test/iroh-bistream-debug.js +38 -0
  112. package/dist/test/iroh-communication.test.js +66 -0
  113. package/dist/test/iroh-debug-test.js +57 -0
  114. package/dist/test/iroh-diap-test.js +71 -0
  115. package/dist/test/iroh-direct-connect.js +55 -0
  116. package/dist/test/iroh-e2e-fixed.js +89 -0
  117. package/dist/test/iroh-e2e-same-process.js +63 -0
  118. package/dist/test/iroh-e2e.js +66 -0
  119. package/dist/test/iroh-final-e2e.js +72 -0
  120. package/dist/test/iroh-relay-test.js +37 -0
  121. package/dist/test/iroh-simple-test.js +41 -0
  122. package/dist/test/iroh-transport-verify.js +54 -0
  123. package/dist/test/iroh-transport.test.js +37 -0
  124. package/dist/test/iroh-two-nodes.js +70 -0
  125. package/dist/test/iroh-verify.js +44 -0
  126. package/dist/test/judgment-decision.test.js +219 -0
  127. package/dist/test/llm-judgment-integration.test.js +220 -0
  128. package/dist/test/p2p-agent-complex-dialogue.js +385 -0
  129. package/dist/test/p2p-agent-dialogue.js +341 -0
  130. package/dist/test/p2p-agent-full-bidirectional.js +510 -0
  131. package/dist/test/p2p-agent-harness-flow.js +437 -0
  132. package/dist/test/p2p-agent-harness-single.js +143 -0
  133. package/dist/test/p2p-ai-dialogue-test.js +318 -0
  134. package/dist/test/p2p-cid-connect-test.js +195 -0
  135. package/dist/test/p2p-connect-receiver.js +69 -0
  136. package/dist/test/p2p-doc-transfer.js +110 -0
  137. package/dist/test/p2p-identity-page-test.js +77 -0
  138. package/dist/test/p2p-iroh-test.js +171 -0
  139. package/dist/test/p2p-minimal-test.js +241 -0
  140. package/dist/test/p2p-node-1.js +148 -0
  141. package/dist/test/p2p-node-2.js +148 -0
  142. package/dist/test/p2p-server.js +281 -0
  143. package/dist/test/p2p-two-nodes-test.js +438 -0
  144. package/dist/test/pi-sdk.test.js +44 -0
  145. package/dist/test/set-persona.js +40 -0
  146. package/dist/test/simple.test.js +9 -0
  147. package/dist/test/storage-integration.test.js +150 -0
  148. package/dist/test/subagent-manager.test.js +276 -0
  149. package/dist/test/test-gate-flow.test.js +81 -0
  150. package/dist/test/workflow-engine.test.js +87 -0
  151. package/dist/test/workflow-pivot-loop.test.js +246 -0
  152. package/dist/web/api-config.html +779 -779
  153. package/dist/web/client-hearth.js +10 -10
  154. package/dist/web/client.js +54 -0
  155. package/dist/web/components/wallet-viem.mjs +118 -118
  156. package/dist/web/delivery-ledger.js +103 -0
  157. package/dist/web/i18n.js +104 -0
  158. package/dist/web/index.html +472 -472
  159. package/dist/web/manifest.json +20 -20
  160. package/dist/web/routes-tasks.js +242 -24
  161. package/dist/web/server-storage.js +111 -0
  162. package/dist/web/server.js +55 -26
  163. package/dist/web/style.css +4946 -4946
  164. package/dist/web/task-breaker.js +18 -0
  165. package/dist/web/task-cancel.js +35 -0
  166. package/dist/web/task-deps.js +36 -0
  167. package/dist/web/task-review.js +27 -0
  168. package/dist/web/task-verify.js +60 -0
  169. package/package.json +196 -193
  170. package/scripts/build-cli.js +215 -215
  171. package/scripts/build-web.ts +130 -130
  172. package/scripts/postinstall.js +152 -152
  173. package/bin/bolloon-daemon.sh +0 -207
  174. package/dist/constraint-runtime/reference_data/archive_surface_snapshot.json +0 -63
  175. package/dist/constraint-runtime/reference_data/commands_snapshot.json +0 -1037
  176. package/dist/constraint-runtime/reference_data/subsystems/assistant.json +0 -8
  177. package/dist/constraint-runtime/reference_data/subsystems/bootstrap.json +0 -8
  178. package/dist/constraint-runtime/reference_data/subsystems/bridge.json +0 -32
  179. package/dist/constraint-runtime/reference_data/subsystems/buddy.json +0 -13
  180. package/dist/constraint-runtime/reference_data/subsystems/cli.json +0 -26
  181. package/dist/constraint-runtime/reference_data/subsystems/components.json +0 -32
  182. package/dist/constraint-runtime/reference_data/subsystems/constants.json +0 -28
  183. package/dist/constraint-runtime/reference_data/subsystems/coordinator.json +0 -8
  184. package/dist/constraint-runtime/reference_data/subsystems/entrypoints.json +0 -15
  185. package/dist/constraint-runtime/reference_data/subsystems/hooks.json +0 -32
  186. package/dist/constraint-runtime/reference_data/subsystems/keybindings.json +0 -21
  187. package/dist/constraint-runtime/reference_data/subsystems/memdir.json +0 -15
  188. package/dist/constraint-runtime/reference_data/subsystems/migrations.json +0 -18
  189. package/dist/constraint-runtime/reference_data/subsystems/moreright.json +0 -8
  190. package/dist/constraint-runtime/reference_data/subsystems/native_ts.json +0 -11
  191. package/dist/constraint-runtime/reference_data/subsystems/outputStyles.json +0 -8
  192. package/dist/constraint-runtime/reference_data/subsystems/plugins.json +0 -9
  193. package/dist/constraint-runtime/reference_data/subsystems/remote.json +0 -11
  194. package/dist/constraint-runtime/reference_data/subsystems/schemas.json +0 -8
  195. package/dist/constraint-runtime/reference_data/subsystems/screens.json +0 -10
  196. package/dist/constraint-runtime/reference_data/subsystems/server.json +0 -10
  197. package/dist/constraint-runtime/reference_data/subsystems/services.json +0 -32
  198. package/dist/constraint-runtime/reference_data/subsystems/skills.json +0 -27
  199. package/dist/constraint-runtime/reference_data/subsystems/state.json +0 -13
  200. package/dist/constraint-runtime/reference_data/subsystems/types.json +0 -18
  201. package/dist/constraint-runtime/reference_data/subsystems/upstreamproxy.json +0 -9
  202. package/dist/constraint-runtime/reference_data/subsystems/utils.json +0 -32
  203. package/dist/constraint-runtime/reference_data/subsystems/vim.json +0 -12
  204. package/dist/constraint-runtime/reference_data/subsystems/voice.json +0 -8
  205. package/dist/constraint-runtime/reference_data/tools_snapshot.json +0 -922
  206. package/dist/electron/config.js.map +0 -1
  207. package/dist/electron/dialogs.js.map +0 -1
  208. package/dist/electron/first-run.js.map +0 -1
  209. package/dist/electron/ipc.js.map +0 -1
  210. package/dist/electron/logger.js.map +0 -1
  211. package/dist/electron/main.js.map +0 -1
  212. package/dist/electron/menu.js.map +0 -1
  213. package/dist/electron/paths.js.map +0 -1
  214. package/dist/electron/server.js.map +0 -1
  215. package/dist/electron/tray.js.map +0 -1
  216. package/dist/electron/window.js.map +0 -1
  217. package/dist/utils/auto-update.js.map +0 -1
  218. package/dist/web/client.js.map +0 -7
@@ -9,60 +9,60 @@ import * as fs from 'fs';
9
9
  import * as path from 'path';
10
10
  import { firstRunFlagPath, dataDir, logsDir } from './paths';
11
11
  import { log } from './logger';
12
- const OVERLAY_HTML = `
13
- <!DOCTYPE html>
14
- <html>
15
- <head>
16
- <meta charset="utf-8" />
17
- <style>
18
- :root { color-scheme: light dark; }
19
- body {
20
- font-family: -apple-system, BlinkMacSystemFont, "Segoe UI", sans-serif;
21
- margin: 0; padding: 32px 28px;
22
- background: rgba(245,245,247,0.97);
23
- color: #1d1d1f;
24
- height: 100vh; box-sizing: border-box;
25
- }
26
- @media (prefers-color-scheme: dark) {
27
- body { background: rgba(28,28,30,0.97); color: #f5f5f7; }
28
- }
29
- h1 { font-size: 18px; margin: 0 0 14px; font-weight: 600; }
30
- p { font-size: 13px; line-height: 1.55; margin: 8px 0; }
31
- code {
32
- font-family: ui-monospace, "SF Mono", Menlo, monospace;
33
- font-size: 12px; padding: 1px 5px;
34
- background: rgba(0,0,0,0.06); border-radius: 3px;
35
- }
36
- @media (prefers-color-scheme: dark) {
37
- code { background: rgba(255,255,255,0.08); }
38
- }
39
- .btn {
40
- display: inline-block; margin-top: 18px; padding: 8px 18px;
41
- background: #007aff; color: #fff; border: none; border-radius: 6px;
42
- font-size: 13px; font-weight: 500; cursor: pointer;
43
- }
44
- .btn:hover { background: #0066d6; }
45
- ul { padding-left: 20px; }
46
- li { font-size: 13px; line-height: 1.7; }
47
- </style>
48
- </head>
49
- <body>
50
- <h1>欢迎使用 Bolloon Agent</h1>
51
- <p>你的数据存放在本地, 不上传:</p>
52
- <ul>
53
- <li>配置 / 频道 / P2P 密钥: <code id="data"></code></li>
54
- <li>运行日志: <code id="logs"></code></li>
55
- </ul>
56
- <p>所有数据在卸载后仍保留 — 想清理就手动删除 ~/.bolloon/。</p>
57
- <button class="btn" id="ok">知道了</button>
58
- <script>
59
- const ok = document.getElementById('ok');
60
- ok.addEventListener('click', () => window.electronAPI.markFirstRunSeen());
61
- document.getElementById('data').textContent = window.electronAPI.getDataPathSync?.() || '';
62
- document.getElementById('logs').textContent = window.electronAPI.getLogsPathSync?.() || '';
63
- </script>
64
- </body>
65
- </html>
12
+ const OVERLAY_HTML = `
13
+ <!DOCTYPE html>
14
+ <html>
15
+ <head>
16
+ <meta charset="utf-8" />
17
+ <style>
18
+ :root { color-scheme: light dark; }
19
+ body {
20
+ font-family: -apple-system, BlinkMacSystemFont, "Segoe UI", sans-serif;
21
+ margin: 0; padding: 32px 28px;
22
+ background: rgba(245,245,247,0.97);
23
+ color: #1d1d1f;
24
+ height: 100vh; box-sizing: border-box;
25
+ }
26
+ @media (prefers-color-scheme: dark) {
27
+ body { background: rgba(28,28,30,0.97); color: #f5f5f7; }
28
+ }
29
+ h1 { font-size: 18px; margin: 0 0 14px; font-weight: 600; }
30
+ p { font-size: 13px; line-height: 1.55; margin: 8px 0; }
31
+ code {
32
+ font-family: ui-monospace, "SF Mono", Menlo, monospace;
33
+ font-size: 12px; padding: 1px 5px;
34
+ background: rgba(0,0,0,0.06); border-radius: 3px;
35
+ }
36
+ @media (prefers-color-scheme: dark) {
37
+ code { background: rgba(255,255,255,0.08); }
38
+ }
39
+ .btn {
40
+ display: inline-block; margin-top: 18px; padding: 8px 18px;
41
+ background: #007aff; color: #fff; border: none; border-radius: 6px;
42
+ font-size: 13px; font-weight: 500; cursor: pointer;
43
+ }
44
+ .btn:hover { background: #0066d6; }
45
+ ul { padding-left: 20px; }
46
+ li { font-size: 13px; line-height: 1.7; }
47
+ </style>
48
+ </head>
49
+ <body>
50
+ <h1>欢迎使用 Bolloon Agent</h1>
51
+ <p>你的数据存放在本地, 不上传:</p>
52
+ <ul>
53
+ <li>配置 / 频道 / P2P 密钥: <code id="data"></code></li>
54
+ <li>运行日志: <code id="logs"></code></li>
55
+ </ul>
56
+ <p>所有数据在卸载后仍保留 — 想清理就手动删除 ~/.bolloon/。</p>
57
+ <button class="btn" id="ok">知道了</button>
58
+ <script>
59
+ const ok = document.getElementById('ok');
60
+ ok.addEventListener('click', () => window.electronAPI.markFirstRunSeen());
61
+ document.getElementById('data').textContent = window.electronAPI.getDataPathSync?.() || '';
62
+ document.getElementById('logs').textContent = window.electronAPI.getLogsPathSync?.() || '';
63
+ </script>
64
+ </body>
65
+ </html>
66
66
  `;
67
67
  export function hasSeenFirstRun() {
68
68
  try {
@@ -49,60 +49,60 @@ const fs = __importStar(require("fs"));
49
49
  const path = __importStar(require("path"));
50
50
  const paths_1 = require("./paths");
51
51
  const logger_1 = require("./logger");
52
- const OVERLAY_HTML = `
53
- <!DOCTYPE html>
54
- <html>
55
- <head>
56
- <meta charset="utf-8" />
57
- <style>
58
- :root { color-scheme: light dark; }
59
- body {
60
- font-family: -apple-system, BlinkMacSystemFont, "Segoe UI", sans-serif;
61
- margin: 0; padding: 32px 28px;
62
- background: rgba(245,245,247,0.97);
63
- color: #1d1d1f;
64
- height: 100vh; box-sizing: border-box;
65
- }
66
- @media (prefers-color-scheme: dark) {
67
- body { background: rgba(28,28,30,0.97); color: #f5f5f7; }
68
- }
69
- h1 { font-size: 18px; margin: 0 0 14px; font-weight: 600; }
70
- p { font-size: 13px; line-height: 1.55; margin: 8px 0; }
71
- code {
72
- font-family: ui-monospace, "SF Mono", Menlo, monospace;
73
- font-size: 12px; padding: 1px 5px;
74
- background: rgba(0,0,0,0.06); border-radius: 3px;
75
- }
76
- @media (prefers-color-scheme: dark) {
77
- code { background: rgba(255,255,255,0.08); }
78
- }
79
- .btn {
80
- display: inline-block; margin-top: 18px; padding: 8px 18px;
81
- background: #007aff; color: #fff; border: none; border-radius: 6px;
82
- font-size: 13px; font-weight: 500; cursor: pointer;
83
- }
84
- .btn:hover { background: #0066d6; }
85
- ul { padding-left: 20px; }
86
- li { font-size: 13px; line-height: 1.7; }
87
- </style>
88
- </head>
89
- <body>
90
- <h1>欢迎使用 Bolloon Agent</h1>
91
- <p>你的数据存放在本地, 不上传:</p>
92
- <ul>
93
- <li>配置 / 频道 / P2P 密钥: <code id="data"></code></li>
94
- <li>运行日志: <code id="logs"></code></li>
95
- </ul>
96
- <p>所有数据在卸载后仍保留 — 想清理就手动删除 ~/.bolloon/。</p>
97
- <button class="btn" id="ok">知道了</button>
98
- <script>
99
- const ok = document.getElementById('ok');
100
- ok.addEventListener('click', () => window.electronAPI.markFirstRunSeen());
101
- document.getElementById('data').textContent = window.electronAPI.getDataPathSync?.() || '';
102
- document.getElementById('logs').textContent = window.electronAPI.getLogsPathSync?.() || '';
103
- </script>
104
- </body>
105
- </html>
52
+ const OVERLAY_HTML = `
53
+ <!DOCTYPE html>
54
+ <html>
55
+ <head>
56
+ <meta charset="utf-8" />
57
+ <style>
58
+ :root { color-scheme: light dark; }
59
+ body {
60
+ font-family: -apple-system, BlinkMacSystemFont, "Segoe UI", sans-serif;
61
+ margin: 0; padding: 32px 28px;
62
+ background: rgba(245,245,247,0.97);
63
+ color: #1d1d1f;
64
+ height: 100vh; box-sizing: border-box;
65
+ }
66
+ @media (prefers-color-scheme: dark) {
67
+ body { background: rgba(28,28,30,0.97); color: #f5f5f7; }
68
+ }
69
+ h1 { font-size: 18px; margin: 0 0 14px; font-weight: 600; }
70
+ p { font-size: 13px; line-height: 1.55; margin: 8px 0; }
71
+ code {
72
+ font-family: ui-monospace, "SF Mono", Menlo, monospace;
73
+ font-size: 12px; padding: 1px 5px;
74
+ background: rgba(0,0,0,0.06); border-radius: 3px;
75
+ }
76
+ @media (prefers-color-scheme: dark) {
77
+ code { background: rgba(255,255,255,0.08); }
78
+ }
79
+ .btn {
80
+ display: inline-block; margin-top: 18px; padding: 8px 18px;
81
+ background: #007aff; color: #fff; border: none; border-radius: 6px;
82
+ font-size: 13px; font-weight: 500; cursor: pointer;
83
+ }
84
+ .btn:hover { background: #0066d6; }
85
+ ul { padding-left: 20px; }
86
+ li { font-size: 13px; line-height: 1.7; }
87
+ </style>
88
+ </head>
89
+ <body>
90
+ <h1>欢迎使用 Bolloon Agent</h1>
91
+ <p>你的数据存放在本地, 不上传:</p>
92
+ <ul>
93
+ <li>配置 / 频道 / P2P 密钥: <code id="data"></code></li>
94
+ <li>运行日志: <code id="logs"></code></li>
95
+ </ul>
96
+ <p>所有数据在卸载后仍保留 — 想清理就手动删除 ~/.bolloon/。</p>
97
+ <button class="btn" id="ok">知道了</button>
98
+ <script>
99
+ const ok = document.getElementById('ok');
100
+ ok.addEventListener('click', () => window.electronAPI.markFirstRunSeen());
101
+ document.getElementById('data').textContent = window.electronAPI.getDataPathSync?.() || '';
102
+ document.getElementById('logs').textContent = window.electronAPI.getLogsPathSync?.() || '';
103
+ </script>
104
+ </body>
105
+ </html>
106
106
  `;
107
107
  function hasSeenFirstRun() {
108
108
  try {
@@ -1 +1 @@
1
- {"version":3,"file":"electron-preload.js","sourceRoot":"","sources":["../src/electron-preload.ts"],"names":[],"mappings":";;AAAA;;;;GAIG;AACH,uCAAwE;AAIxE,wBAAa,CAAC,iBAAiB,CAAC,aAAa,EAAE;IAC7C,kBAAkB;IAClB,UAAU,EAAE,GAAG,EAAE,CAAC,sBAAW,CAAC,MAAM,CAAC,aAAa,CAAC;IACnD,eAAe,EAAE,GAAG,EAAE,CAAC,sBAAW,CAAC,MAAM,CAAC,oBAAoB,CAAC;IAC/D,YAAY,EAAE,CAAC,GAAW,EAAE,EAAE,CAAC,sBAAW,CAAC,MAAM,CAAC,eAAe,EAAE,GAAG,CAAC;IAEvE,mBAAmB;IACnB,WAAW,EAAE,GAAG,EAAE,CAAC,sBAAW,CAAC,MAAM,CAAC,eAAe,CAAC;IAEtD,wBAAwB;IACxB,QAAQ,EAAE,CAAC,IAAU,EAAE,EAAE,CAAC,sBAAW,CAAC,MAAM,CAAC,kBAAkB,EAAE,IAAI,CAAC;IACtE,QAAQ,EAAE,CAAC,IAAU,EAAE,EAAE,CAAC,sBAAW,CAAC,MAAM,CAAC,kBAAkB,EAAE,IAAI,CAAC;IACtE,aAAa,EAAE,CAAC,IAAU,EAAE,EAAE,CAAC,sBAAW,CAAC,MAAM,CAAC,uBAAuB,EAAE,IAAI,CAAC;IAEhF,gCAAgC;IAChC,YAAY,EAAE,CAAC,IAAyC,EAAE,EAAE,CAC1D,sBAAW,CAAC,MAAM,CAAC,mBAAmB,EAAE,IAAI,CAAC;IAC/C,aAAa,EAAE,CAAC,IAA0D,EAAE,EAAE,CAC5E,sBAAW,CAAC,MAAM,CAAC,oBAAoB,EAAE,IAAI,CAAC;IAChD,UAAU,EAAE,CAAC,IAAsB,EAAE,EAAE,CAAC,sBAAW,CAAC,MAAM,CAAC,gBAAgB,EAAE,IAAI,CAAC;IAElF,mBAAmB;IACnB,eAAe,EAAE,GAAG,EAAE,CAAC,sBAAW,CAAC,MAAM,CAAC,gBAAgB,CAAC;IAC3D,gBAAgB,EAAE,GAAG,EAAE,CAAC,sBAAW,CAAC,MAAM,CAAC,qBAAqB,CAAC;IACjE,eAAe,EAAE,GAAG,EAAE,CAAC,sBAAW,CAAC,MAAM,CAAC,oBAAoB,CAAC;IAC/D,eAAe,EAAE,GAAG,EAAE,CAAC,sBAAW,CAAC,MAAM,CAAC,oBAAoB,CAAC;IAE/D,cAAc;IACd,QAAQ,EAAE,OAAO,CAAC,QAAQ;CAC3B,CAAC,CAAC"}
1
+ {"version":3,"file":"electron-preload.js","sourceRoot":"","sources":["../src/electron-preload.ts"],"names":[],"mappings":";;AAAA;;;GAGG;AACH,uCAAsD;AAEtD,eAAe;AACf,wBAAa,CAAC,iBAAiB,CAAC,aAAa,EAAE;IAC7C,UAAU,EAAE,GAAG,EAAE,CAAC,sBAAW,CAAC,MAAM,CAAC,aAAa,CAAC;IACnD,eAAe,EAAE,GAAG,EAAE,CAAC,sBAAW,CAAC,MAAM,CAAC,oBAAoB,CAAC;IAC/D,YAAY,EAAE,CAAC,GAAW,EAAE,EAAE,CAAC,sBAAW,CAAC,MAAM,CAAC,eAAe,EAAE,GAAG,CAAC;IACvE,QAAQ,EAAE,OAAO,CAAC,QAAQ;CAC3B,CAAC,CAAC"}
@@ -1 +1 @@
1
- {"version":3,"file":"electron.js","sourceRoot":"","sources":["../src/electron.ts"],"names":[],"mappings":";;AAAA;;;GAGG;AACH,2BAAyB"}
1
+ {"version":3,"file":"electron.js","sourceRoot":"","sources":["../src/electron.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,70 @@
1
+ /**
2
+ * delegate-handle.ts — 委派句柄 (借鉴 Hermes Agent `agent/subagent_lifecycle.py` 的 handle 设计)
3
+ *
4
+ * Hermes 模式: 子任务 handle 是不可变契约 + HMAC 签名 capability,
5
+ * `capability = HMAC(secret, subagent_id|parent_session_id|created_at)`,
6
+ * 校验时 strict 类型检查 + `hmac.compare_digest` 定时安全比对 + 父 session 必须匹配。
7
+ * 子 agent 拿到 handle 也伪造不了、跨 session 用不了 — 防提权。
8
+ *
9
+ * Bolloon 对应物: delegate_to_engine 的委派记录。
10
+ * - 父身份用 `ownerDid` (agent 的 DID, 稳定跨重启; 比 sessionId 更适合防跨 channel)
11
+ * - handle 写入 sidechain JSONL 落盘, 可事后验证记录真实性 (防伪造委派记录)
12
+ * - correlationId 支持幂等去重 (同一 parent+correlation 只允许一次)
13
+ */
14
+ import { createHmac, randomBytes, randomUUID, timingSafeEqual } from 'crypto';
15
+ /** 契约版本: 结构不兼容时递增, 旧 handle 直接拒绝而不是猜字段 */
16
+ export const DELEGATE_CONTRACT_VERSION = 1;
17
+ /**
18
+ * 进程级随机密钥 (与 Hermes `_SECRET = secrets.token_bytes(32)` 同思路):
19
+ * 每次启动重新生成 → 重启后的旧 handle 全部失效, 序列化 handle 不可重放。
20
+ */
21
+ const _SECRET = randomBytes(32);
22
+ function _capability(delegateId, ownerDid, createdAt) {
23
+ return createHmac('sha256', _SECRET)
24
+ .update(`${delegateId}|${ownerDid}|${createdAt}`)
25
+ .digest('hex');
26
+ }
27
+ /** 创建委派句柄 (与 Hermes launch() 返回 SubagentHandle 对应) */
28
+ export function createDelegateHandle(opts) {
29
+ const delegateId = randomUUID();
30
+ const createdAt = Date.now();
31
+ return {
32
+ contractVersion: DELEGATE_CONTRACT_VERSION,
33
+ delegateId,
34
+ ownerDid: opts.ownerDid,
35
+ correlationId: opts.correlationId,
36
+ createdAt,
37
+ engineId: opts.engineId,
38
+ model: opts.model,
39
+ capability: _capability(delegateId, opts.ownerDid, createdAt),
40
+ };
41
+ }
42
+ /**
43
+ * 校验句柄真实性。
44
+ * @param ownerDid 传当前活跃父 DID → 额外强制匹配 (防跨 channel/跨 agent 使用)
45
+ */
46
+ export function verifyDelegateHandle(handle, ownerDid) {
47
+ if (!handle || typeof handle !== 'object')
48
+ return false;
49
+ const h = handle;
50
+ // strict 类型检查 (Hermes `_record` 同款): 类型不对直接拒, 不猜
51
+ if (h.contractVersion !== DELEGATE_CONTRACT_VERSION)
52
+ return false;
53
+ if (typeof h.delegateId !== 'string' || h.delegateId === '')
54
+ return false;
55
+ if (typeof h.ownerDid !== 'string' || h.ownerDid === '')
56
+ return false;
57
+ if (typeof h.createdAt !== 'number' || !Number.isFinite(h.createdAt))
58
+ return false;
59
+ if (typeof h.engineId !== 'string' || h.engineId === '')
60
+ return false;
61
+ if (typeof h.capability !== 'string' || h.capability === '')
62
+ return false;
63
+ if (ownerDid !== undefined && h.ownerDid !== ownerDid)
64
+ return false;
65
+ // 定时安全比对 (与 hmac.compare_digest 等价)
66
+ const expected = _capability(h.delegateId, h.ownerDid, h.createdAt);
67
+ const a = Buffer.from(h.capability, 'hex');
68
+ const b = Buffer.from(expected, 'hex');
69
+ return a.length === b.length && timingSafeEqual(a, b);
70
+ }
@@ -14,6 +14,7 @@ import * as fs from 'fs/promises';
14
14
  import * as path from 'path';
15
15
  import * as os from 'os';
16
16
  import { discoverEngines, buildDelegateArgs } from './discovery.js';
17
+ import { createDelegateHandle } from './delegate-handle.js';
17
18
  function delegateTimeoutMs() {
18
19
  const env = Number(process.env.BOLLOON_ENGINE_DELEGATE_TIMEOUT_MS);
19
20
  return Number.isFinite(env) && env > 0 ? env : 120_000;
@@ -57,6 +58,15 @@ export async function delegateToEngine(id, prompt, opts = {}) {
57
58
  }
58
59
  const cwd = opts.cwd || process.cwd();
59
60
  const timeoutMs = opts.timeoutMs || delegateTimeoutMs();
61
+ // Hermes 模式: 委派句柄 — HMAC 签名, 随 sidechain 落盘, 返回给调用方供事后验证
62
+ const handle = opts.ownerDid
63
+ ? createDelegateHandle({
64
+ ownerDid: opts.ownerDid,
65
+ engineId: trimmedId,
66
+ correlationId: opts.correlationId,
67
+ model: opts.model,
68
+ })
69
+ : undefined;
60
70
  return new Promise((resolve) => {
61
71
  let stdout = '';
62
72
  let stderr = '';
@@ -137,6 +147,7 @@ export async function delegateToEngine(id, prompt, opts = {}) {
137
147
  killTree();
138
148
  const combined = (stdout + (stderr ? `\n[stderr]\n${stderr}` : '')).trim();
139
149
  // 2026-07-29: Sidechain transcript — 保存委派完整记录
150
+ // 2026-08-11: 记录带 HMAC 签名 handle (contract_version + capability), 可事后验真
140
151
  try {
141
152
  const sidechainDir = path.join(os.homedir(), '.bolloon', 'sidechains');
142
153
  fs.mkdir(sidechainDir, { recursive: true });
@@ -147,19 +158,29 @@ export async function delegateToEngine(id, prompt, opts = {}) {
147
158
  stdout: stdout.slice(0, 100_000),
148
159
  stderr: stderr.slice(0, 10_000),
149
160
  exitCode: code, duration: Date.now() - ts, model: opts.model || null,
161
+ handle: handle ? {
162
+ contractVersion: handle.contractVersion,
163
+ delegateId: handle.delegateId,
164
+ ownerDid: handle.ownerDid,
165
+ correlationId: handle.correlationId ?? null,
166
+ createdAt: handle.createdAt,
167
+ engineId: handle.engineId,
168
+ model: handle.model ?? null,
169
+ capability: handle.capability,
170
+ } : null,
150
171
  }) + '\n';
151
172
  // fire-and-forget, 不阻塞主流程
152
173
  fs.appendFile(filePath, entry, 'utf-8').catch(() => { });
153
174
  }
154
175
  catch { /* sidechain 写入失败静默 */ }
155
176
  if (code === 0) {
156
- resolve({ success: true, output: combined || '(无输出)', exitCode: code });
177
+ resolve({ success: true, output: combined || '(无输出)', exitCode: code, handle });
157
178
  }
158
179
  else if (signal) {
159
- resolve({ success: false, output: combined || '(无输出)', error: `${trimmedId} 被信号 ${signal} 终止`, exitCode: null });
180
+ resolve({ success: false, output: combined || '(无输出)', error: `${trimmedId} 被信号 ${signal} 终止`, exitCode: null, handle });
160
181
  }
161
182
  else {
162
- resolve({ success: false, output: combined || '(无输出)', error: `${trimmedId} 退出码 ${code}`, exitCode: code });
183
+ resolve({ success: false, output: combined || '(无输出)', error: `${trimmedId} 退出码 ${code}`, exitCode: code, handle });
163
184
  }
164
185
  });
165
186
  });
package/dist/index.js CHANGED
@@ -1874,10 +1874,10 @@ async function runToolCommand(tool, args, outputJson, comm, model, prompt) {
1874
1874
  const running = irohTransport.isRunning();
1875
1875
  const irohPeers = irohTransport.getPeers();
1876
1876
  const messenger = hybridMessenger ? 'HybridMessenger 就绪' : 'HybridMessenger 未初始化';
1877
- response = `iroh P2P 状态:
1878
- 运行中: ${running ? '是' : '否'}
1879
- Node ID: ${nodeId ? nodeId.substring(0, 32) + '...' : 'N/A'}
1880
- 已知节点: ${irohPeers.length}
1877
+ response = `iroh P2P 状态:
1878
+ 运行中: ${running ? '是' : '否'}
1879
+ Node ID: ${nodeId ? nodeId.substring(0, 32) + '...' : 'N/A'}
1880
+ 已知节点: ${irohPeers.length}
1881
1881
  ${messenger}`;
1882
1882
  break;
1883
1883
  }
@@ -3011,114 +3011,114 @@ function parseArgs() {
3011
3011
  return result;
3012
3012
  }
3013
3013
  function printHelp() {
3014
- console.log(`
3015
- 🤖 Bolloon Agent - AI 可调用文档处理智能体
3016
-
3017
- 用法:
3018
- npx tsx src/index.ts [选项] [参数]
3019
-
3020
- 选项:
3021
- # 文档处理
3022
- --read <file> 读取文档 (txt, md, pdf, docx)
3023
- --summarize <file> [ctx] 总结文档,可选上下文
3024
- --improve <file> <req> 改进文档,req 为改进要求
3025
-
3026
- # P2P 网络
3027
- --peers 列出已连接的对等节点
3028
- --broadcast <msg> 广播消息到所有节点
3029
- --send <peerId> <msg> 向指定节点发送消息
3030
-
3031
- # 智能体
3032
- --identity 显示当前智能体身份
3033
- --logs 显示操作日志
3034
- --search <keyword> 搜索文件
3035
- --tools 显示所有可用工具
3036
-
3037
- # SubAgent 管理
3038
- --agents 列出所有 SubAgent
3039
- --register-agent <name> [cap1] [cap2]... 注册新 SubAgent
3040
- --delegate <任务描述> [能力要求...] 委派任务给最佳 Agent
3041
-
3042
- # 全局共享上下文
3043
- --context 显示全局共享上下文摘要
3044
- --global-agents 显示全局 Agent 注册表
3045
- --add-action <内容> [重要性] 添加用户行动到共享上下文
3046
-
3047
- # Bollharness 治理框架
3048
- --harness-init 初始化 Bollharness 治理框架
3049
- --harness-gate 显示当前 Gate 状态
3050
- --harness-transition [PASS|BLOCK] 执行 Gate 转移
3051
- --harness-skill <name> [action] 执行 Harness Skill
3052
- --harness-classify <描述> 分类变更类型
3053
- --harness-context <file> 获取文件上下文
3054
- --harness-check <file> 执行 Guard 检查
3055
- --harness-archive 归档当前 Session 到 Harness
3056
- --harness-sessions 列出 Session 归档记录
3057
- --harness-session-context [id] 获取 Session 上下文
3058
-
3059
- # 自动更新
3060
- --update-check 检查 npm 包更新
3061
- --update-now [pkg] 更新到最新版本
3062
-
3063
- # 跨机聊天 (commits-as-messages, 共享 GitHub 仓库)
3064
- --chat-init 初始化 .comm/ 目录 (一次性)
3065
- --chat-send "消息正文" 把消息写到 .comm/<role>/, commit + push
3066
- --chat-pull 拉取远端 .comm/ 的新消息并显示
3067
- --chat-list 列出本地所有已同步消息
3068
- --chat-watch [--interval 15s] 后台定时拉取, 有新消息时输出
3069
- --chat-status 一屏查看: role / publicKey / remote / ahead-behind
3070
-
3071
- # 纯 P2P 私聊 (不走 GitHub, 不写 git, 不持久化)
3072
- --chat-p2p-send <peer|publicKey> "消息正文" 通过 P2P 直接发一条
3073
- --chat-p2p-listen 后台监听对方 P2P 私聊消息 (Ctrl-C 退出)
3074
-
3075
- # 跨机 agent 协作 (对方 bolloon --web 起着才能处理, 走 P2P 不经 GitHub)
3076
- --collab <peer|publicKey> "<任务描述>" 派任务给对端 LLM 干活, 等回结果 (90s 超时)
3077
-
3078
- # 外部编码智能体委派
3079
- --engine, -e <id> [--model <m>] <prompt> 委派任务给外部引擎,如 opencode/codex
3080
- --model <name> 指定委派时使用的模型
3081
-
3082
- # 输出控制
3083
- --json, -j 输出 JSON 格式
3084
- --output, -o <file> 结果保存到文件
3085
- --web 启动 Web UI 模式
3086
- --help, -h 显示帮助信息
3087
-
3088
- 示例:
3089
- # 文档处理
3090
- npx tsx src/index.ts --read 想法.md
3091
- npx tsx src/index.ts --summarize docs/想法.md
3092
- npx tsx src/index.ts --improve docs/README.md "让内容更简洁"
3093
- npx tsx src/index.ts --read 想法.md -o summary.txt
3094
-
3095
- # P2P 网络
3096
- npx tsx src/index.ts --peers
3097
- npx tsx src/index.ts --broadcast "Hello everyone"
3098
- npx tsx src/index.ts --send QmABC... "私信内容"
3099
-
3100
- # AI 对话
3101
- npx tsx src/index.ts --prompt "总结 README.md"
3102
- npx tsx src/index.ts -p "分析这个项目" -j
3103
-
3104
- # 交互模式
3105
- npx tsx src/index.ts
3106
-
3107
- # 外部引擎委派
3108
- npx tsx src/index.ts --engine opencode --model opencode/deepseek-v4-flash-free "说你好"
3109
-
3110
- # Web 模式
3111
- npx tsx src/index.ts --web
3112
-
3113
- 环境变量:
3114
- MINIMAX_API_KEY MiniMax API 密钥
3115
- DEEPSEEK_API_KEY DeepSeek API 密钥
3116
- KIMI_API_KEY / MOONSHOT_API_KEY Kimi/Moonshot API 密钥
3117
- GLM_API_KEY / ZHIPU_API_KEY 智谱 GLM API 密钥
3118
- QWEN_API_KEY / DASHSCOPE_API_KEY 通义千问 API 密钥
3119
- OPENAI_API_KEY OpenAI API 密钥(Pi SDK)
3120
- ANTHROPIC_API_KEY Anthropic API 密钥(Pi SDK)
3121
- PORT Web 服务端口(默认 54188)
3014
+ console.log(`
3015
+ 🤖 Bolloon Agent - AI 可调用文档处理智能体
3016
+
3017
+ 用法:
3018
+ npx tsx src/index.ts [选项] [参数]
3019
+
3020
+ 选项:
3021
+ # 文档处理
3022
+ --read <file> 读取文档 (txt, md, pdf, docx)
3023
+ --summarize <file> [ctx] 总结文档,可选上下文
3024
+ --improve <file> <req> 改进文档,req 为改进要求
3025
+
3026
+ # P2P 网络
3027
+ --peers 列出已连接的对等节点
3028
+ --broadcast <msg> 广播消息到所有节点
3029
+ --send <peerId> <msg> 向指定节点发送消息
3030
+
3031
+ # 智能体
3032
+ --identity 显示当前智能体身份
3033
+ --logs 显示操作日志
3034
+ --search <keyword> 搜索文件
3035
+ --tools 显示所有可用工具
3036
+
3037
+ # SubAgent 管理
3038
+ --agents 列出所有 SubAgent
3039
+ --register-agent <name> [cap1] [cap2]... 注册新 SubAgent
3040
+ --delegate <任务描述> [能力要求...] 委派任务给最佳 Agent
3041
+
3042
+ # 全局共享上下文
3043
+ --context 显示全局共享上下文摘要
3044
+ --global-agents 显示全局 Agent 注册表
3045
+ --add-action <内容> [重要性] 添加用户行动到共享上下文
3046
+
3047
+ # Bollharness 治理框架
3048
+ --harness-init 初始化 Bollharness 治理框架
3049
+ --harness-gate 显示当前 Gate 状态
3050
+ --harness-transition [PASS|BLOCK] 执行 Gate 转移
3051
+ --harness-skill <name> [action] 执行 Harness Skill
3052
+ --harness-classify <描述> 分类变更类型
3053
+ --harness-context <file> 获取文件上下文
3054
+ --harness-check <file> 执行 Guard 检查
3055
+ --harness-archive 归档当前 Session 到 Harness
3056
+ --harness-sessions 列出 Session 归档记录
3057
+ --harness-session-context [id] 获取 Session 上下文
3058
+
3059
+ # 自动更新
3060
+ --update-check 检查 npm 包更新
3061
+ --update-now [pkg] 更新到最新版本
3062
+
3063
+ # 跨机聊天 (commits-as-messages, 共享 GitHub 仓库)
3064
+ --chat-init 初始化 .comm/ 目录 (一次性)
3065
+ --chat-send "消息正文" 把消息写到 .comm/<role>/, commit + push
3066
+ --chat-pull 拉取远端 .comm/ 的新消息并显示
3067
+ --chat-list 列出本地所有已同步消息
3068
+ --chat-watch [--interval 15s] 后台定时拉取, 有新消息时输出
3069
+ --chat-status 一屏查看: role / publicKey / remote / ahead-behind
3070
+
3071
+ # 纯 P2P 私聊 (不走 GitHub, 不写 git, 不持久化)
3072
+ --chat-p2p-send <peer|publicKey> "消息正文" 通过 P2P 直接发一条
3073
+ --chat-p2p-listen 后台监听对方 P2P 私聊消息 (Ctrl-C 退出)
3074
+
3075
+ # 跨机 agent 协作 (对方 bolloon --web 起着才能处理, 走 P2P 不经 GitHub)
3076
+ --collab <peer|publicKey> "<任务描述>" 派任务给对端 LLM 干活, 等回结果 (90s 超时)
3077
+
3078
+ # 外部编码智能体委派
3079
+ --engine, -e <id> [--model <m>] <prompt> 委派任务给外部引擎,如 opencode/codex
3080
+ --model <name> 指定委派时使用的模型
3081
+
3082
+ # 输出控制
3083
+ --json, -j 输出 JSON 格式
3084
+ --output, -o <file> 结果保存到文件
3085
+ --web 启动 Web UI 模式
3086
+ --help, -h 显示帮助信息
3087
+
3088
+ 示例:
3089
+ # 文档处理
3090
+ npx tsx src/index.ts --read 想法.md
3091
+ npx tsx src/index.ts --summarize docs/想法.md
3092
+ npx tsx src/index.ts --improve docs/README.md "让内容更简洁"
3093
+ npx tsx src/index.ts --read 想法.md -o summary.txt
3094
+
3095
+ # P2P 网络
3096
+ npx tsx src/index.ts --peers
3097
+ npx tsx src/index.ts --broadcast "Hello everyone"
3098
+ npx tsx src/index.ts --send QmABC... "私信内容"
3099
+
3100
+ # AI 对话
3101
+ npx tsx src/index.ts --prompt "总结 README.md"
3102
+ npx tsx src/index.ts -p "分析这个项目" -j
3103
+
3104
+ # 交互模式
3105
+ npx tsx src/index.ts
3106
+
3107
+ # 外部引擎委派
3108
+ npx tsx src/index.ts --engine opencode --model opencode/deepseek-v4-flash-free "说你好"
3109
+
3110
+ # Web 模式
3111
+ npx tsx src/index.ts --web
3112
+
3113
+ 环境变量:
3114
+ MINIMAX_API_KEY MiniMax API 密钥
3115
+ DEEPSEEK_API_KEY DeepSeek API 密钥
3116
+ KIMI_API_KEY / MOONSHOT_API_KEY Kimi/Moonshot API 密钥
3117
+ GLM_API_KEY / ZHIPU_API_KEY 智谱 GLM API 密钥
3118
+ QWEN_API_KEY / DASHSCOPE_API_KEY 通义千问 API 密钥
3119
+ OPENAI_API_KEY OpenAI API 密钥(Pi SDK)
3120
+ ANTHROPIC_API_KEY Anthropic API 密钥(Pi SDK)
3121
+ PORT Web 服务端口(默认 54188)
3122
3122
  `);
3123
3123
  }
3124
3124
  // ---------------------------------------------------------------------------