@oddessentials/agent-guild 0.1.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 (342) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +162 -0
  3. package/bin/agent-guild-report.mjs +134 -0
  4. package/bin/agent-guild.mjs +240 -0
  5. package/config/providers.default.json +124 -0
  6. package/examples/claude-code-settings.json +48 -0
  7. package/examples/codex-hooks.json +45 -0
  8. package/examples/gemini-settings.json +61 -0
  9. package/examples/grok-hooks.json +55 -0
  10. package/examples/providers.json +27 -0
  11. package/node_modules/@xterm/addon-fit/LICENSE +19 -0
  12. package/node_modules/@xterm/addon-fit/README.md +24 -0
  13. package/node_modules/@xterm/addon-fit/lib/addon-fit.js +2 -0
  14. package/node_modules/@xterm/addon-fit/lib/addon-fit.js.map +1 -0
  15. package/node_modules/@xterm/addon-fit/lib/addon-fit.mjs +18 -0
  16. package/node_modules/@xterm/addon-fit/lib/addon-fit.mjs.map +7 -0
  17. package/node_modules/@xterm/addon-fit/package.json +26 -0
  18. package/node_modules/@xterm/addon-fit/src/FitAddon.ts +92 -0
  19. package/node_modules/@xterm/addon-fit/typings/addon-fit.d.ts +55 -0
  20. package/node_modules/@xterm/addon-serialize/README.md +42 -0
  21. package/node_modules/@xterm/addon-serialize/lib/addon-serialize.js +2 -0
  22. package/node_modules/@xterm/addon-serialize/lib/addon-serialize.js.map +1 -0
  23. package/node_modules/@xterm/addon-serialize/lib/addon-serialize.mjs +19 -0
  24. package/node_modules/@xterm/addon-serialize/lib/addon-serialize.mjs.map +7 -0
  25. package/node_modules/@xterm/addon-serialize/package.json +29 -0
  26. package/node_modules/@xterm/addon-serialize/src/SerializeAddon.ts +695 -0
  27. package/node_modules/@xterm/addon-serialize/typings/addon-serialize.d.ts +116 -0
  28. package/node_modules/@xterm/addon-web-links/LICENSE +19 -0
  29. package/node_modules/@xterm/addon-web-links/README.md +21 -0
  30. package/node_modules/@xterm/addon-web-links/lib/addon-web-links.js +2 -0
  31. package/node_modules/@xterm/addon-web-links/lib/addon-web-links.js.map +1 -0
  32. package/node_modules/@xterm/addon-web-links/lib/addon-web-links.mjs +18 -0
  33. package/node_modules/@xterm/addon-web-links/lib/addon-web-links.mjs.map +7 -0
  34. package/node_modules/@xterm/addon-web-links/package.json +26 -0
  35. package/node_modules/@xterm/addon-web-links/src/WebLinkProvider.ts +199 -0
  36. package/node_modules/@xterm/addon-web-links/src/WebLinksAddon.ts +58 -0
  37. package/node_modules/@xterm/addon-web-links/typings/addon-web-links.d.ts +57 -0
  38. package/node_modules/@xterm/headless/README.md +31 -0
  39. package/node_modules/@xterm/headless/lib-headless/xterm-headless.js +2 -0
  40. package/node_modules/@xterm/headless/lib-headless/xterm-headless.js.map +1 -0
  41. package/node_modules/@xterm/headless/lib-headless/xterm-headless.mjs +46 -0
  42. package/node_modules/@xterm/headless/lib-headless/xterm-headless.mjs.map +7 -0
  43. package/node_modules/@xterm/headless/package.json +29 -0
  44. package/node_modules/@xterm/headless/typings/xterm-headless.d.ts +1385 -0
  45. package/node_modules/@xterm/xterm/LICENSE +21 -0
  46. package/node_modules/@xterm/xterm/README.md +243 -0
  47. package/node_modules/@xterm/xterm/css/xterm.css +285 -0
  48. package/node_modules/@xterm/xterm/lib/xterm.js +2 -0
  49. package/node_modules/@xterm/xterm/lib/xterm.js.map +1 -0
  50. package/node_modules/@xterm/xterm/lib/xterm.mjs +53 -0
  51. package/node_modules/@xterm/xterm/lib/xterm.mjs.map +7 -0
  52. package/node_modules/@xterm/xterm/package.json +111 -0
  53. package/node_modules/@xterm/xterm/src/browser/AccessibilityManager.ts +435 -0
  54. package/node_modules/@xterm/xterm/src/browser/Clipboard.ts +93 -0
  55. package/node_modules/@xterm/xterm/src/browser/ColorContrastCache.ts +34 -0
  56. package/node_modules/@xterm/xterm/src/browser/CoreBrowserTerminal.ts +1339 -0
  57. package/node_modules/@xterm/xterm/src/browser/Linkifier.ts +403 -0
  58. package/node_modules/@xterm/xterm/src/browser/LocalizableStrings.ts +23 -0
  59. package/node_modules/@xterm/xterm/src/browser/OscLinkProvider.ts +129 -0
  60. package/node_modules/@xterm/xterm/src/browser/RenderDebouncer.ts +84 -0
  61. package/node_modules/@xterm/xterm/src/browser/TimeBasedDebouncer.ts +86 -0
  62. package/node_modules/@xterm/xterm/src/browser/Types.ts +226 -0
  63. package/node_modules/@xterm/xterm/src/browser/Viewport.ts +192 -0
  64. package/node_modules/@xterm/xterm/src/browser/decorations/BufferDecorationRenderer.ts +139 -0
  65. package/node_modules/@xterm/xterm/src/browser/decorations/ColorZoneStore.ts +117 -0
  66. package/node_modules/@xterm/xterm/src/browser/decorations/OverviewRulerRenderer.ts +214 -0
  67. package/node_modules/@xterm/xterm/src/browser/input/CompositionHelper.ts +248 -0
  68. package/node_modules/@xterm/xterm/src/browser/input/Mouse.ts +54 -0
  69. package/node_modules/@xterm/xterm/src/browser/input/MoveToCell.ts +251 -0
  70. package/node_modules/@xterm/xterm/src/browser/public/Terminal.ts +275 -0
  71. package/node_modules/@xterm/xterm/src/browser/renderer/dom/DomRenderer.ts +542 -0
  72. package/node_modules/@xterm/xterm/src/browser/renderer/dom/DomRendererRowFactory.ts +546 -0
  73. package/node_modules/@xterm/xterm/src/browser/renderer/dom/WidthCache.ts +167 -0
  74. package/node_modules/@xterm/xterm/src/browser/renderer/shared/Constants.ts +6 -0
  75. package/node_modules/@xterm/xterm/src/browser/renderer/shared/RendererUtils.ts +95 -0
  76. package/node_modules/@xterm/xterm/src/browser/renderer/shared/SelectionRenderModel.ts +93 -0
  77. package/node_modules/@xterm/xterm/src/browser/renderer/shared/Types.ts +84 -0
  78. package/node_modules/@xterm/xterm/src/browser/selection/SelectionModel.ts +144 -0
  79. package/node_modules/@xterm/xterm/src/browser/selection/Types.ts +15 -0
  80. package/node_modules/@xterm/xterm/src/browser/services/CharSizeService.ts +127 -0
  81. package/node_modules/@xterm/xterm/src/browser/services/CharacterJoinerService.ts +339 -0
  82. package/node_modules/@xterm/xterm/src/browser/services/CoreBrowserService.ts +137 -0
  83. package/node_modules/@xterm/xterm/src/browser/services/LinkProviderService.ts +28 -0
  84. package/node_modules/@xterm/xterm/src/browser/services/MouseService.ts +46 -0
  85. package/node_modules/@xterm/xterm/src/browser/services/RenderService.ts +376 -0
  86. package/node_modules/@xterm/xterm/src/browser/services/SelectionService.ts +1039 -0
  87. package/node_modules/@xterm/xterm/src/browser/services/Services.ts +158 -0
  88. package/node_modules/@xterm/xterm/src/browser/services/ThemeService.ts +198 -0
  89. package/node_modules/@xterm/xterm/src/browser/shared/Constants.ts +8 -0
  90. package/node_modules/@xterm/xterm/src/common/CircularList.ts +241 -0
  91. package/node_modules/@xterm/xterm/src/common/Clone.ts +23 -0
  92. package/node_modules/@xterm/xterm/src/common/Color.ts +376 -0
  93. package/node_modules/@xterm/xterm/src/common/CoreTerminal.ts +283 -0
  94. package/node_modules/@xterm/xterm/src/common/InputHandler.ts +3495 -0
  95. package/node_modules/@xterm/xterm/src/common/MultiKeyMap.ts +42 -0
  96. package/node_modules/@xterm/xterm/src/common/Platform.ts +44 -0
  97. package/node_modules/@xterm/xterm/src/common/SortedList.ts +194 -0
  98. package/node_modules/@xterm/xterm/src/common/TaskQueue.ts +166 -0
  99. package/node_modules/@xterm/xterm/src/common/TypedArrayUtils.ts +17 -0
  100. package/node_modules/@xterm/xterm/src/common/Types.ts +552 -0
  101. package/node_modules/@xterm/xterm/src/common/WindowsMode.ts +27 -0
  102. package/node_modules/@xterm/xterm/src/common/buffer/AttributeData.ts +211 -0
  103. package/node_modules/@xterm/xterm/src/common/buffer/Buffer.ts +662 -0
  104. package/node_modules/@xterm/xterm/src/common/buffer/BufferLine.ts +551 -0
  105. package/node_modules/@xterm/xterm/src/common/buffer/BufferRange.ts +13 -0
  106. package/node_modules/@xterm/xterm/src/common/buffer/BufferReflow.ts +226 -0
  107. package/node_modules/@xterm/xterm/src/common/buffer/BufferSet.ts +134 -0
  108. package/node_modules/@xterm/xterm/src/common/buffer/CellData.ts +94 -0
  109. package/node_modules/@xterm/xterm/src/common/buffer/Constants.ts +157 -0
  110. package/node_modules/@xterm/xterm/src/common/buffer/Marker.ts +43 -0
  111. package/node_modules/@xterm/xterm/src/common/buffer/Types.ts +52 -0
  112. package/node_modules/@xterm/xterm/src/common/data/Charsets.ts +256 -0
  113. package/node_modules/@xterm/xterm/src/common/data/EscapeSequences.ts +153 -0
  114. package/node_modules/@xterm/xterm/src/common/input/Keyboard.ts +373 -0
  115. package/node_modules/@xterm/xterm/src/common/input/TextDecoder.ts +346 -0
  116. package/node_modules/@xterm/xterm/src/common/input/UnicodeV6.ts +145 -0
  117. package/node_modules/@xterm/xterm/src/common/input/WriteBuffer.ts +247 -0
  118. package/node_modules/@xterm/xterm/src/common/input/XParseColor.ts +80 -0
  119. package/node_modules/@xterm/xterm/src/common/parser/Constants.ts +58 -0
  120. package/node_modules/@xterm/xterm/src/common/parser/DcsParser.ts +192 -0
  121. package/node_modules/@xterm/xterm/src/common/parser/EscapeSequenceParser.ts +792 -0
  122. package/node_modules/@xterm/xterm/src/common/parser/OscParser.ts +238 -0
  123. package/node_modules/@xterm/xterm/src/common/parser/Params.ts +229 -0
  124. package/node_modules/@xterm/xterm/src/common/parser/Types.ts +275 -0
  125. package/node_modules/@xterm/xterm/src/common/public/AddonManager.ts +53 -0
  126. package/node_modules/@xterm/xterm/src/common/public/BufferApiView.ts +35 -0
  127. package/node_modules/@xterm/xterm/src/common/public/BufferLineApiView.ts +29 -0
  128. package/node_modules/@xterm/xterm/src/common/public/BufferNamespaceApi.ts +36 -0
  129. package/node_modules/@xterm/xterm/src/common/public/ParserApi.ts +37 -0
  130. package/node_modules/@xterm/xterm/src/common/public/UnicodeApi.ts +27 -0
  131. package/node_modules/@xterm/xterm/src/common/services/BufferService.ts +154 -0
  132. package/node_modules/@xterm/xterm/src/common/services/CharsetService.ts +34 -0
  133. package/node_modules/@xterm/xterm/src/common/services/CoreMouseService.ts +365 -0
  134. package/node_modules/@xterm/xterm/src/common/services/CoreService.ts +92 -0
  135. package/node_modules/@xterm/xterm/src/common/services/DecorationService.ts +140 -0
  136. package/node_modules/@xterm/xterm/src/common/services/InstantiationService.ts +85 -0
  137. package/node_modules/@xterm/xterm/src/common/services/LogService.ts +124 -0
  138. package/node_modules/@xterm/xterm/src/common/services/OptionsService.ts +212 -0
  139. package/node_modules/@xterm/xterm/src/common/services/OscLinkService.ts +115 -0
  140. package/node_modules/@xterm/xterm/src/common/services/ServiceRegistry.ts +49 -0
  141. package/node_modules/@xterm/xterm/src/common/services/Services.ts +396 -0
  142. package/node_modules/@xterm/xterm/src/common/services/UnicodeService.ts +111 -0
  143. package/node_modules/@xterm/xterm/src/vs/base/browser/browser.ts +141 -0
  144. package/node_modules/@xterm/xterm/src/vs/base/browser/canIUse.ts +49 -0
  145. package/node_modules/@xterm/xterm/src/vs/base/browser/dom.ts +2369 -0
  146. package/node_modules/@xterm/xterm/src/vs/base/browser/fastDomNode.ts +316 -0
  147. package/node_modules/@xterm/xterm/src/vs/base/browser/globalPointerMoveMonitor.ts +112 -0
  148. package/node_modules/@xterm/xterm/src/vs/base/browser/iframe.ts +135 -0
  149. package/node_modules/@xterm/xterm/src/vs/base/browser/keyboardEvent.ts +213 -0
  150. package/node_modules/@xterm/xterm/src/vs/base/browser/mouseEvent.ts +229 -0
  151. package/node_modules/@xterm/xterm/src/vs/base/browser/touch.ts +372 -0
  152. package/node_modules/@xterm/xterm/src/vs/base/browser/ui/scrollbar/abstractScrollbar.ts +303 -0
  153. package/node_modules/@xterm/xterm/src/vs/base/browser/ui/scrollbar/horizontalScrollbar.ts +114 -0
  154. package/node_modules/@xterm/xterm/src/vs/base/browser/ui/scrollbar/scrollableElement.ts +720 -0
  155. package/node_modules/@xterm/xterm/src/vs/base/browser/ui/scrollbar/scrollableElementOptions.ts +165 -0
  156. package/node_modules/@xterm/xterm/src/vs/base/browser/ui/scrollbar/scrollbarArrow.ts +114 -0
  157. package/node_modules/@xterm/xterm/src/vs/base/browser/ui/scrollbar/scrollbarState.ts +243 -0
  158. package/node_modules/@xterm/xterm/src/vs/base/browser/ui/scrollbar/scrollbarVisibilityController.ts +118 -0
  159. package/node_modules/@xterm/xterm/src/vs/base/browser/ui/scrollbar/verticalScrollbar.ts +116 -0
  160. package/node_modules/@xterm/xterm/src/vs/base/browser/ui/widget.ts +57 -0
  161. package/node_modules/@xterm/xterm/src/vs/base/browser/window.ts +14 -0
  162. package/node_modules/@xterm/xterm/src/vs/base/common/arrays.ts +887 -0
  163. package/node_modules/@xterm/xterm/src/vs/base/common/arraysFind.ts +202 -0
  164. package/node_modules/@xterm/xterm/src/vs/base/common/assert.ts +71 -0
  165. package/node_modules/@xterm/xterm/src/vs/base/common/async.ts +1992 -0
  166. package/node_modules/@xterm/xterm/src/vs/base/common/cancellation.ts +148 -0
  167. package/node_modules/@xterm/xterm/src/vs/base/common/charCode.ts +450 -0
  168. package/node_modules/@xterm/xterm/src/vs/base/common/collections.ts +140 -0
  169. package/node_modules/@xterm/xterm/src/vs/base/common/decorators.ts +130 -0
  170. package/node_modules/@xterm/xterm/src/vs/base/common/equals.ts +146 -0
  171. package/node_modules/@xterm/xterm/src/vs/base/common/errors.ts +303 -0
  172. package/node_modules/@xterm/xterm/src/vs/base/common/event.ts +1778 -0
  173. package/node_modules/@xterm/xterm/src/vs/base/common/functional.ts +32 -0
  174. package/node_modules/@xterm/xterm/src/vs/base/common/hash.ts +316 -0
  175. package/node_modules/@xterm/xterm/src/vs/base/common/iterator.ts +159 -0
  176. package/node_modules/@xterm/xterm/src/vs/base/common/keyCodes.ts +526 -0
  177. package/node_modules/@xterm/xterm/src/vs/base/common/keybindings.ts +284 -0
  178. package/node_modules/@xterm/xterm/src/vs/base/common/lazy.ts +47 -0
  179. package/node_modules/@xterm/xterm/src/vs/base/common/lifecycle.ts +801 -0
  180. package/node_modules/@xterm/xterm/src/vs/base/common/linkedList.ts +142 -0
  181. package/node_modules/@xterm/xterm/src/vs/base/common/map.ts +202 -0
  182. package/node_modules/@xterm/xterm/src/vs/base/common/numbers.ts +98 -0
  183. package/node_modules/@xterm/xterm/src/vs/base/common/observable.ts +76 -0
  184. package/node_modules/@xterm/xterm/src/vs/base/common/observableInternal/api.ts +31 -0
  185. package/node_modules/@xterm/xterm/src/vs/base/common/observableInternal/autorun.ts +281 -0
  186. package/node_modules/@xterm/xterm/src/vs/base/common/observableInternal/base.ts +489 -0
  187. package/node_modules/@xterm/xterm/src/vs/base/common/observableInternal/debugName.ts +145 -0
  188. package/node_modules/@xterm/xterm/src/vs/base/common/observableInternal/derived.ts +428 -0
  189. package/node_modules/@xterm/xterm/src/vs/base/common/observableInternal/lazyObservableValue.ts +146 -0
  190. package/node_modules/@xterm/xterm/src/vs/base/common/observableInternal/logging.ts +328 -0
  191. package/node_modules/@xterm/xterm/src/vs/base/common/observableInternal/promise.ts +209 -0
  192. package/node_modules/@xterm/xterm/src/vs/base/common/observableInternal/utils.ts +610 -0
  193. package/node_modules/@xterm/xterm/src/vs/base/common/platform.ts +281 -0
  194. package/node_modules/@xterm/xterm/src/vs/base/common/scrollable.ts +522 -0
  195. package/node_modules/@xterm/xterm/src/vs/base/common/sequence.ts +34 -0
  196. package/node_modules/@xterm/xterm/src/vs/base/common/stopwatch.ts +43 -0
  197. package/node_modules/@xterm/xterm/src/vs/base/common/strings.ts +557 -0
  198. package/node_modules/@xterm/xterm/src/vs/base/common/symbols.ts +9 -0
  199. package/node_modules/@xterm/xterm/src/vs/base/common/uint.ts +59 -0
  200. package/node_modules/@xterm/xterm/src/vs/patches/nls.ts +90 -0
  201. package/node_modules/@xterm/xterm/src/vs/typings/base-common.d.ts +20 -0
  202. package/node_modules/@xterm/xterm/src/vs/typings/require.d.ts +42 -0
  203. package/node_modules/@xterm/xterm/src/vs/typings/vscode-globals-nls.d.ts +36 -0
  204. package/node_modules/@xterm/xterm/src/vs/typings/vscode-globals-product.d.ts +33 -0
  205. package/node_modules/@xterm/xterm/typings/xterm.d.ts +1957 -0
  206. package/node_modules/node-addon-api/LICENSE.md +9 -0
  207. package/node_modules/node-addon-api/README.md +319 -0
  208. package/node_modules/node-addon-api/common.gypi +20 -0
  209. package/node_modules/node-addon-api/except.gypi +25 -0
  210. package/node_modules/node-addon-api/index.js +12 -0
  211. package/node_modules/node-addon-api/napi-inl.deprecated.h +186 -0
  212. package/node_modules/node-addon-api/napi-inl.h +6607 -0
  213. package/node_modules/node-addon-api/napi.h +3201 -0
  214. package/node_modules/node-addon-api/node_addon_api.gyp +32 -0
  215. package/node_modules/node-addon-api/node_api.gyp +9 -0
  216. package/node_modules/node-addon-api/noexcept.gypi +26 -0
  217. package/node_modules/node-addon-api/nothing.c +0 -0
  218. package/node_modules/node-addon-api/package-support.json +21 -0
  219. package/node_modules/node-addon-api/package.json +480 -0
  220. package/node_modules/node-addon-api/tools/README.md +73 -0
  221. package/node_modules/node-addon-api/tools/check-napi.js +99 -0
  222. package/node_modules/node-addon-api/tools/clang-format.js +71 -0
  223. package/node_modules/node-addon-api/tools/conversion.js +301 -0
  224. package/node_modules/node-addon-api/tools/eslint-format.js +79 -0
  225. package/node_modules/node-pty/LICENSE +69 -0
  226. package/node_modules/node-pty/README.md +164 -0
  227. package/node_modules/node-pty/binding.gyp +150 -0
  228. package/node_modules/node-pty/lib/conpty_console_list_agent.js +25 -0
  229. package/node_modules/node-pty/lib/eventEmitter2.js +47 -0
  230. package/node_modules/node-pty/lib/index.js +52 -0
  231. package/node_modules/node-pty/lib/interfaces.js +7 -0
  232. package/node_modules/node-pty/lib/shared/conout.js +10 -0
  233. package/node_modules/node-pty/lib/terminal.js +190 -0
  234. package/node_modules/node-pty/lib/types.js +7 -0
  235. package/node_modules/node-pty/lib/unixTerminal.js +351 -0
  236. package/node_modules/node-pty/lib/utils.js +38 -0
  237. package/node_modules/node-pty/lib/windowsConoutConnection.js +131 -0
  238. package/node_modules/node-pty/lib/windowsPtyAgent.js +344 -0
  239. package/node_modules/node-pty/lib/windowsTerminal.js +209 -0
  240. package/node_modules/node-pty/lib/worker/conoutSocketWorker.js +22 -0
  241. package/node_modules/node-pty/package.json +66 -0
  242. package/node_modules/node-pty/prebuilds/darwin-arm64/pty.node +0 -0
  243. package/node_modules/node-pty/prebuilds/darwin-arm64/spawn-helper +0 -0
  244. package/node_modules/node-pty/prebuilds/darwin-x64/pty.node +0 -0
  245. package/node_modules/node-pty/prebuilds/darwin-x64/spawn-helper +0 -0
  246. package/node_modules/node-pty/prebuilds/linux-arm64/pty.node +0 -0
  247. package/node_modules/node-pty/prebuilds/linux-x64/pty.node +0 -0
  248. package/node_modules/node-pty/prebuilds/win32-arm64/conpty/OpenConsole.exe +0 -0
  249. package/node_modules/node-pty/prebuilds/win32-arm64/conpty/conpty.dll +0 -0
  250. package/node_modules/node-pty/prebuilds/win32-arm64/conpty.node +0 -0
  251. package/node_modules/node-pty/prebuilds/win32-arm64/conpty.pdb +0 -0
  252. package/node_modules/node-pty/prebuilds/win32-arm64/conpty_console_list.node +0 -0
  253. package/node_modules/node-pty/prebuilds/win32-arm64/conpty_console_list.pdb +0 -0
  254. package/node_modules/node-pty/prebuilds/win32-x64/conpty/OpenConsole.exe +0 -0
  255. package/node_modules/node-pty/prebuilds/win32-x64/conpty/conpty.dll +0 -0
  256. package/node_modules/node-pty/prebuilds/win32-x64/conpty.node +0 -0
  257. package/node_modules/node-pty/prebuilds/win32-x64/conpty.pdb +0 -0
  258. package/node_modules/node-pty/prebuilds/win32-x64/conpty_console_list.node +0 -0
  259. package/node_modules/node-pty/prebuilds/win32-x64/conpty_console_list.pdb +0 -0
  260. package/node_modules/node-pty/scripts/post-install.js +76 -0
  261. package/node_modules/node-pty/scripts/prebuild.js +34 -0
  262. package/node_modules/node-pty/src/unix/pty.cc +876 -0
  263. package/node_modules/node-pty/src/unix/spawn-helper.cc +23 -0
  264. package/node_modules/node-pty/src/win/conpty.cc +616 -0
  265. package/node_modules/node-pty/src/win/conpty.h +41 -0
  266. package/node_modules/node-pty/src/win/conpty_console_list.cc +44 -0
  267. package/node_modules/node-pty/src/win/path_util.cc +95 -0
  268. package/node_modules/node-pty/src/win/path_util.h +26 -0
  269. package/node_modules/node-pty/third_party/conpty/1.25.260303002/win10-arm64/OpenConsole.exe +0 -0
  270. package/node_modules/node-pty/third_party/conpty/1.25.260303002/win10-arm64/conpty.dll +0 -0
  271. package/node_modules/node-pty/third_party/conpty/1.25.260303002/win10-x64/OpenConsole.exe +0 -0
  272. package/node_modules/node-pty/third_party/conpty/1.25.260303002/win10-x64/conpty.dll +0 -0
  273. package/node_modules/node-pty/typings/node-pty.d.ts +215 -0
  274. package/node_modules/ws/LICENSE +20 -0
  275. package/node_modules/ws/README.md +548 -0
  276. package/node_modules/ws/browser.js +8 -0
  277. package/node_modules/ws/index.js +22 -0
  278. package/node_modules/ws/lib/buffer-util.js +131 -0
  279. package/node_modules/ws/lib/constants.js +19 -0
  280. package/node_modules/ws/lib/event-target.js +292 -0
  281. package/node_modules/ws/lib/extension.js +203 -0
  282. package/node_modules/ws/lib/limiter.js +55 -0
  283. package/node_modules/ws/lib/permessage-deflate.js +530 -0
  284. package/node_modules/ws/lib/receiver.js +743 -0
  285. package/node_modules/ws/lib/sender.js +607 -0
  286. package/node_modules/ws/lib/stream.js +161 -0
  287. package/node_modules/ws/lib/subprotocol.js +62 -0
  288. package/node_modules/ws/lib/validation.js +152 -0
  289. package/node_modules/ws/lib/websocket-server.js +562 -0
  290. package/node_modules/ws/lib/websocket.js +1421 -0
  291. package/node_modules/ws/package.json +74 -0
  292. package/node_modules/ws/wrapper.mjs +21 -0
  293. package/package.json +52 -0
  294. package/src/manager/command-resolver.mjs +140 -0
  295. package/src/manager/config.mjs +94 -0
  296. package/src/manager/install-channels.mjs +268 -0
  297. package/src/manager/main.mjs +136 -0
  298. package/src/manager/providers.mjs +601 -0
  299. package/src/manager/report-shims.mjs +104 -0
  300. package/src/manager/server.mjs +421 -0
  301. package/src/manager/session-manager.mjs +306 -0
  302. package/src/manager/session.mjs +531 -0
  303. package/src/manager/shell-env.mjs +150 -0
  304. package/src/manager/usage.mjs +535 -0
  305. package/src/manager/versions.mjs +62 -0
  306. package/src/report/hooks.mjs +150 -0
  307. package/web/app.js +916 -0
  308. package/web/art/art.css +186 -0
  309. package/web/art/characters/anthropic/idle.png +0 -0
  310. package/web/art/characters/anthropic/locked.png +0 -0
  311. package/web/art/characters/anthropic/working.png +0 -0
  312. package/web/art/characters/google/idle.png +0 -0
  313. package/web/art/characters/google/locked.png +0 -0
  314. package/web/art/characters/google/working.png +0 -0
  315. package/web/art/characters/openai/idle.png +0 -0
  316. package/web/art/characters/openai/locked.png +0 -0
  317. package/web/art/characters/openai/working.png +0 -0
  318. package/web/art/characters/shell/idle.png +0 -0
  319. package/web/art/characters/shell/locked.png +0 -0
  320. package/web/art/characters/shell/working.png +0 -0
  321. package/web/art/characters/xai/idle.png +0 -0
  322. package/web/art/characters/xai/locked.png +0 -0
  323. package/web/art/characters/xai/working.png +0 -0
  324. package/web/art/familiars/aether.png +0 -0
  325. package/web/art/familiars/flame.png +0 -0
  326. package/web/art/familiars/leaf.png +0 -0
  327. package/web/art/familiars/night.png +0 -0
  328. package/web/art/icons/anthropic.png +0 -0
  329. package/web/art/icons/google.png +0 -0
  330. package/web/art/icons/openai.png +0 -0
  331. package/web/art/icons/shell.png +0 -0
  332. package/web/art/icons/xai.png +0 -0
  333. package/web/art/page.png +0 -0
  334. package/web/art/ui/frame.png +0 -0
  335. package/web/art/ui/gem-mana.png +0 -0
  336. package/web/art/ui/gem-vitality.png +0 -0
  337. package/web/art/ui/guild-crest.png +0 -0
  338. package/web/art/ui/level-medallion.png +0 -0
  339. package/web/art/ui/padlock.png +0 -0
  340. package/web/icons/README.md +8 -0
  341. package/web/index.html +154 -0
  342. package/web/styles.css +226 -0
package/LICENSE ADDED
@@ -0,0 +1,21 @@
1
+ MIT License
2
+
3
+ Copyright (c) 2026 Odd Essentials
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.
package/README.md ADDED
@@ -0,0 +1,162 @@
1
+ # Agent Guild
2
+
3
+ Agent Guild runs AI coding assistants side by side from one local web page.
4
+ Pick a provider, get a real interactive terminal running that provider's
5
+ coding tool, and see at a glance which sessions and agents are working.
6
+
7
+ ![Agent Guild session cards](docs/screenshot.png)
8
+
9
+ * **Start sessions from provider cards.** Anthropic (Claude Code), OpenAI
10
+ (Codex CLI), Google (Gemini CLI), xAI (Grok Build), and a plain shell.
11
+ **New** starts a fresh session; **Existing** resumes one of
12
+ the tool's own earlier sessions from its id. Providers whose tool is not
13
+ installed are shown greyed out with an **Install** button that runs
14
+ `npm install -g` in a session you can watch, or with install instructions
15
+ when the tool is not an npm package. Installed tools show their version
16
+ and an **Update** button; updating while that tool's sessions are running
17
+ asks first, because it can break them.
18
+ * **See what is left of your limits.** Claude Code, Codex CLI and Gemini
19
+ CLI cards show a meter per rate-limit window (5-hour, 7-day, or per
20
+ model, including Claude's weekly Fable window and the model and feature
21
+ limits Codex meters separately) with the time until it resets, read from
22
+ the tool's own sign-in.
23
+ Claude's extra-usage spend and Codex's prepaid credit balance appear
24
+ when the account has them. Other providers can supply a command that
25
+ prints usage.
26
+ * **Work in real terminals.** Each session is a card. Open it for a full
27
+ interactive terminal: type instructions, answer prompts, watch output. Run
28
+ as many sessions at once as you like.
29
+ * **See agents and models at work.** When a coding tool reports helper
30
+ agents, they appear as small icons on that session's card. The card also
31
+ names the main model in use, reported by the tool or, failing that,
32
+ spotted on its screen.
33
+ * **Close the page any time.** A separate local session manager owns the
34
+ terminals. Reopen the page and it reconnects to the same sessions with
35
+ their screens intact, as long as the manager is still running. Sessions do
36
+ not survive a computer restart. **Stop manager** in the top bar stops the
37
+ manager and ends every session; it asks first while any session is still
38
+ running.
39
+
40
+ ## Requirements
41
+
42
+ * Windows 10 1809 or later, or macOS 11 or later. Linux works for development.
43
+ * Node.js 22 or newer.
44
+ * Each coding tool you want to use, signed in on its own. Agent Guild can
45
+ install the npm-packaged tools for you; it does not authenticate them.
46
+
47
+ node-pty ships prebuilt binaries for Windows, macOS and Linux on x64 and
48
+ arm64, so no compiler is needed. WSL is not required.
49
+
50
+ ## Install and run
51
+
52
+ ```sh
53
+ npm install -g @oddessentials/agent-guild
54
+ agent-guild
55
+ ```
56
+
57
+ `agent-guild open` starts the session manager in the background if needed and
58
+ opens the page. The page URL carries an access token in its `#` fragment. The
59
+ page stores it and then removes it from the address bar.
60
+
61
+ | Command | What it does |
62
+ | --- | --- |
63
+ | `agent-guild` or `agent-guild open` | Start the manager if needed and open the page. `--no-browser` prints the URL instead. |
64
+ | `agent-guild status` | Show whether the manager is running and list its sessions. |
65
+ | `agent-guild stop` | Stop the manager. This ends every session, without asking. The page's **Stop manager** button does the same and asks first while sessions are running. |
66
+ | `agent-guild start` | Run the manager in the foreground, for debugging. |
67
+ | `agent-guild url` | Print the page URL with its token. |
68
+
69
+ ## Configure providers
70
+
71
+ Create `providers.json` in the data folder to change or add providers:
72
+
73
+ | Platform | Data folder |
74
+ | --- | --- |
75
+ | Windows | `%APPDATA%\AgentGuild` |
76
+ | macOS | `~/Library/Application Support/AgentGuild` |
77
+
78
+ Entries are merged with the built-in ones by `id`. A new `id` adds a
79
+ provider, and `"enabled": false` hides one. Any field can be overridden for
80
+ one platform under a `win32` or `darwin` key. See
81
+ [examples/providers.json](examples/providers.json).
82
+
83
+ | Field | Meaning |
84
+ | --- | --- |
85
+ | `id` | Lowercase identifier. |
86
+ | `vendor`, `tool` | Names shown on the icon. |
87
+ | `command`, `args` | What to run. `command` is looked up on PATH. `@shell` means the user's default shell. |
88
+ | `package` | The tool's npm package, e.g. `@openai/codex`. Enables the **Install** button and the version check. |
89
+ | `channels` | How an installed copy is recognised, so **Update** runs that installation's own updater. A copy installed by npm needs no entry. `brew.names` lists the tool's own Homebrew formula or cask names, e.g. `{ "brew": { "names": ["gemini-cli"] } }`, and `winget.id` is its WinGet package id. A provider you add must set these for its Homebrew or WinGet copy to get an **Update** button or a removal command; without them that copy shows as an unknown install with guidance only. `native.paths` are the launcher and folders the vendor's own installer uses, and `native.update` the arguments that make the tool update itself, e.g. `["update"]`. |
90
+ | `versionArgs` | Arguments that make the command print its version, used instead of `args`, e.g. `["--version"]`. |
91
+ | `usage` | Where the usage meters come from: `"claude"`, `"codex"`, `"gemini"`, `{ "command", "args" }` for a program that prints `{ "windows": [{ "label", "usedPercent", "resetsAt" }] }`, or `null` for none. |
92
+ | `modelPattern` | Regular expression that finds the model name on the tool's screen when the tool does not report it. |
93
+ | `resumeArgs` | Arguments that resume the tool's own session, with `{id}` standing for the id, e.g. `["--resume", "{id}"]`. Without it the card has no **Existing** button. |
94
+ | `env` | Extra environment variables for the tool. |
95
+ | `color`, `monogram`, `icon` | Icon appearance. `icon` is a URL path; you can also drop `<id>.svg` into `web/icons/`. |
96
+ | `install`, `docs` | Help shown when the tool is not installed. |
97
+ | `usageUrl`, `billingUrl` | `https://` links to the vendor's usage and billing pages, shown on the card. The defaults point at the subscription pages; set your API console instead, or `null` to hide a link. Google's usage link opens AI Studio, which counts API-key usage only, not the Gemini CLI sign-in quota the card's meters show. |
98
+
99
+ The page's "Working folder" field sets where new sessions start. It defaults
100
+ to your home folder.
101
+
102
+ Version checks ask the registry from npm's global configuration (the one
103
+ `npm install -g` uses) about once an hour, and installs use the same
104
+ registry. Set `AGENT_GUILD_NPM_REGISTRY` to override it for both, or
105
+ `AGENT_GUILD_NO_UPDATE_CHECK=1` to skip the checks.
106
+
107
+ ## Show agents and models
108
+
109
+ Agents are reported by the coding tool, not guessed from its output. Add
110
+ the hooks from the matching file in [examples/](examples/) to Claude Code,
111
+ Codex CLI, Gemini CLI or Grok Build: each sub-agent appears on the card
112
+ while it runs, and the card shows the model in use. The hooks call
113
+ `agent-guild-report`, which the manager puts on the PATH of every session it
114
+ starts, so no global install is needed. Codex CLI runs no hook until you
115
+ trust it (choose "Trust all and continue" when it starts, or run `/hooks`),
116
+ and Claude Code runs none until you accept its workspace-trust prompt. Any
117
+ tool or script can also report agents and the model with the
118
+ `agent-guild-report` command or an escape sequence. See
119
+ [docs/agent-reporting.md](docs/agent-reporting.md).
120
+
121
+ ## Security
122
+
123
+ * The manager listens on `127.0.0.1` only.
124
+ * Every API call needs a random per-user token, stored in the data folder
125
+ with owner-only permissions.
126
+ * Requests with a foreign `Host` or `Origin` header are refused. This stops
127
+ other websites from reaching the terminals through your browser.
128
+ * Tools inside a session get a separate token that can only report agents
129
+ for that session.
130
+ * Usage meters are fetched by the manager with the coding tool's own
131
+ sign-in (Claude Code's credentials, Codex CLI's `auth.json`, Gemini CLI's
132
+ sign-in). The page only ever receives percentages. On macOS the first
133
+ lookup may ask for keychain access to the "Claude Code-credentials" and
134
+ "gemini-cli-oauth" items; choose Always Allow.
135
+
136
+ Anyone who can run programs as your user can already read the token, as with
137
+ any local developer tool.
138
+
139
+ ## Other front ends
140
+
141
+ The page is only one client. The manager's API is documented in
142
+ [docs/api.md](docs/api.md) so that another interface, such as a planned
143
+ Unreal Engine version where provider characters and their workers stand in
144
+ for the icons, can drive the same sessions. See
145
+ [docs/architecture.md](docs/architecture.md).
146
+
147
+ ## Development
148
+
149
+ ```sh
150
+ npm install
151
+ npm test
152
+ ```
153
+
154
+ The tests start real managers and real pseudo-terminals, using a small fake
155
+ coding tool in `tests/fixtures`. CI runs them on Windows, macOS and Linux.
156
+
157
+ ## Current limits
158
+
159
+ * Sessions end when the manager stops or the computer restarts.
160
+ * Gemini CLI usage meters need its sign-in in the OS keychain (macOS, or
161
+ Linux with `secret-tool`) or in the older `oauth_creds.json`; Gemini CLI's
162
+ encrypted-file storage cannot be read.
@@ -0,0 +1,134 @@
1
+ #!/usr/bin/env node
2
+ // Report an agent, or the model in use, inside an Agent Guild session.
3
+ //
4
+ // The session manager injects AGENT_GUILD_URL, AGENT_GUILD_SESSION_ID and
5
+ // AGENT_GUILD_REPORT_TOKEN into every terminal it starts. Outside such a
6
+ // terminal this command does nothing and exits 0, so hooks that call it are
7
+ // harmless when the tool runs elsewhere.
8
+ //
9
+ // agent-guild-report <agent-id> [--name N] [--status working|waiting|idle|done]
10
+ // [--detail TEXT] [--kind KIND] [--remove]
11
+ // agent-guild-report --model NAME [--display-name TEXT]
12
+ // agent-guild-report --hook (reads a hook event as JSON on stdin:
13
+ // Claude Code, Codex CLI, Gemini CLI, Grok Build)
14
+ // agent-guild-report --claude-statusline [--passthrough]
15
+ // (reads Claude Code status line JSON on stdin; prints a
16
+ // status line, or the JSON itself with --passthrough)
17
+
18
+ import { hookToReports, claudeStatuslineToReport, formatStatusLine } from '../src/report/hooks.mjs';
19
+
20
+ const env = process.env;
21
+ const inSession = env.AGENT_GUILD_URL && env.AGENT_GUILD_SESSION_ID && env.AGENT_GUILD_REPORT_TOKEN;
22
+ // Gemini CLI's optional environment redaction removes every variable whose
23
+ // name contains TOKEN before it runs a hook. Say so instead of staying silent.
24
+ if (!inSession && env.AGENT_GUILD_SESSION_ID && !env.AGENT_GUILD_REPORT_TOKEN) {
25
+ console.error('agent-guild-report: AGENT_GUILD_REPORT_TOKEN is missing from the environment; the tool may be redacting variables named *TOKEN*');
26
+ }
27
+
28
+ const USAGE = `Usage: agent-guild-report <agent-id> [--name N] [--status working|waiting|idle|done] [--detail TEXT] [--kind KIND] [--remove]
29
+ agent-guild-report --model NAME [--display-name TEXT]
30
+ agent-guild-report --hook (reads a coding tool's hook event JSON from stdin)
31
+ agent-guild-report --claude-statusline [--passthrough] (reads Claude Code status line JSON from stdin)`;
32
+
33
+ function parseArgs(argv) {
34
+ const out = { positional: [] };
35
+ for (let i = 0; i < argv.length; i++) {
36
+ const a = argv[i];
37
+ if (a === '--remove') out.remove = true;
38
+ else if (a === '--hook' || a === '--claude-hook') out.hook = true;
39
+ else if (a === '--claude-statusline') out.claudeStatusline = true;
40
+ else if (a === '--passthrough') out.passthrough = true;
41
+ else if (a === '-h' || a === '--help') out.help = true;
42
+ else if (a.startsWith('--') && a.includes('=')) {
43
+ const eq = a.indexOf('=');
44
+ out[a.slice(2, eq)] = a.slice(eq + 1);
45
+ } else if (a.startsWith('--')) out[a.slice(2)] = argv[++i];
46
+ else out.positional.push(a);
47
+ }
48
+ return out;
49
+ }
50
+
51
+ function readStdin() {
52
+ return new Promise((resolve) => {
53
+ if (process.stdin.isTTY) return resolve('');
54
+ let data = '';
55
+ process.stdin.setEncoding('utf8');
56
+ process.stdin.on('data', (c) => { data += c; });
57
+ process.stdin.on('end', () => resolve(data));
58
+ process.stdin.on('error', () => resolve(data));
59
+ });
60
+ }
61
+
62
+ async function send(report) {
63
+ const kind = report.agentId !== undefined || report.finishForeground === true ? 'agents' : 'model';
64
+ const url = `${env.AGENT_GUILD_URL}/api/v1/sessions/${env.AGENT_GUILD_SESSION_ID}/${kind}`;
65
+ const res = await fetch(url, {
66
+ method: 'POST',
67
+ headers: {
68
+ 'Content-Type': 'application/json',
69
+ 'X-Agent-Guild-Report-Token': env.AGENT_GUILD_REPORT_TOKEN,
70
+ },
71
+ body: JSON.stringify(report),
72
+ signal: AbortSignal.timeout(3000),
73
+ });
74
+ if (!res.ok) {
75
+ const body = await res.text();
76
+ throw new Error(`HTTP ${res.status}: ${body}`);
77
+ }
78
+ }
79
+
80
+ /** A hook must never break the coding tool, so report failures quietly. */
81
+ const sendQuietly = (report) => send(report).catch((err) => console.error(`agent-guild-report: ${err.message}`));
82
+
83
+ function parseJson(raw) {
84
+ try { return JSON.parse(raw); } catch { return null; }
85
+ }
86
+
87
+ async function main() {
88
+ const args = parseArgs(process.argv.slice(2));
89
+ if (args.help) {
90
+ console.log(USAGE);
91
+ return;
92
+ }
93
+ if (args.hook) {
94
+ const input = parseJson(await readStdin());
95
+ if (!inSession || !input) return;
96
+ for (const report of hookToReports(input)) await sendQuietly(report);
97
+ return;
98
+ }
99
+ if (args.claudeStatusline) {
100
+ const raw = await readStdin();
101
+ const input = parseJson(raw);
102
+ process.stdout.write(args.passthrough ? raw : `${formatStatusLine(input)}\n`);
103
+ if (!inSession || !input) return;
104
+ const report = claudeStatuslineToReport(input);
105
+ if (report) await sendQuietly(report);
106
+ return;
107
+ }
108
+ if (args.model !== undefined && args.positional.length === 0) {
109
+ if (!args.model) {
110
+ console.error('agent-guild-report: --model needs a name');
111
+ process.exitCode = 2;
112
+ return;
113
+ }
114
+ if (!inSession) return;
115
+ await send({ model: args.model, displayName: args['display-name'] });
116
+ return;
117
+ }
118
+ const agentId = args.positional[0];
119
+ if (!agentId) {
120
+ console.error('agent-guild-report: an agent id is required (see --help)');
121
+ process.exitCode = 2;
122
+ return;
123
+ }
124
+ if (!inSession) return;
125
+ const report = { agentId };
126
+ for (const key of ['name', 'status', 'detail', 'kind']) if (args[key] !== undefined) report[key] = args[key];
127
+ if (args.remove) report.remove = true;
128
+ await send(report);
129
+ }
130
+
131
+ main().catch((err) => {
132
+ console.error(`agent-guild-report: ${err.message}`);
133
+ process.exitCode = 1;
134
+ });
@@ -0,0 +1,240 @@
1
+ #!/usr/bin/env node
2
+ // Agent Guild launcher.
3
+ //
4
+ // agent-guild [open] start the session manager if needed, open the page
5
+ // agent-guild start run the session manager in the foreground
6
+ // agent-guild stop stop the manager (ends all sessions)
7
+ // agent-guild status show whether the manager is running
8
+ // agent-guild url print the page URL (includes the access token)
9
+
10
+ import fs from 'node:fs';
11
+ import path from 'node:path';
12
+ import { spawn } from 'node:child_process';
13
+ import { fileURLToPath } from 'node:url';
14
+ import {
15
+ DEFAULT_HOST,
16
+ VERSION,
17
+ ensureDataDir,
18
+ loadOrCreateToken,
19
+ paths,
20
+ readRuntimeFile,
21
+ resolvePort,
22
+ } from '../src/manager/config.mjs';
23
+
24
+ const here = path.dirname(fileURLToPath(import.meta.url));
25
+ const managerEntry = path.resolve(here, '../src/manager/main.mjs');
26
+
27
+ function usage() {
28
+ console.log(`Usage: agent-guild [command] [--no-browser]
29
+
30
+ Commands:
31
+ open Start the session manager if needed and open the web page (default)
32
+ start Run the session manager in the foreground
33
+ stop Stop the session manager and every session it owns
34
+ status Show whether the session manager is running
35
+ url Print the web page URL, including the access token
36
+
37
+ Environment:
38
+ AGENT_GUILD_PORT Port for the local API (default 47821)
39
+ AGENT_GUILD_HOME Data directory (default: per-user app data folder)
40
+ AGENT_GUILD_NPM_REGISTRY npm registry for version checks and installs
41
+ AGENT_GUILD_NO_UPDATE_CHECK Set to 1 to skip version checks`);
42
+ }
43
+
44
+ function baseUrl() {
45
+ const runtime = readRuntimeFile();
46
+ if (runtime?.url) return runtime.url;
47
+ return `http://${DEFAULT_HOST}:${resolvePort()}`;
48
+ }
49
+
50
+ async function health(url, timeoutMs = 1000) {
51
+ try {
52
+ const res = await fetch(`${url}/api/v1/health`, { signal: AbortSignal.timeout(timeoutMs) });
53
+ if (!res.ok) return null;
54
+ const body = await res.json();
55
+ return body?.name === 'agent-guild' ? body : null;
56
+ } catch {
57
+ return null;
58
+ }
59
+ }
60
+
61
+ function pageUrl(url, token) {
62
+ return `${url}/#token=${token}`;
63
+ }
64
+
65
+ function versionNotice(running) {
66
+ if (!running || running === VERSION) return null;
67
+ return `The running manager is version ${running}; the installed Agent Guild is ${VERSION}. ` +
68
+ `Run "agent-guild stop" to end its sessions, then start again to use ${VERSION}.`;
69
+ }
70
+
71
+ function openBrowser(url) {
72
+ const opts = { detached: true, stdio: 'ignore' };
73
+ let child;
74
+ if (process.platform === 'darwin') child = spawn('open', [url], opts);
75
+ else if (process.platform === 'win32') {
76
+ // rundll32 avoids cmd.exe's special handling of characters like "&" in URLs.
77
+ child = spawn('rundll32', ['url.dll,FileProtocolHandler', url], { ...opts, windowsHide: true });
78
+ } else child = spawn('xdg-open', [url], opts);
79
+ child.on('error', () => console.log(`Could not open a browser automatically. Open this URL:\n ${url}`));
80
+ child.unref();
81
+ }
82
+
83
+ function tailLog(lines = 15) {
84
+ try {
85
+ return fs.readFileSync(paths.log, 'utf8').trimEnd().split('\n').slice(-lines).join('\n');
86
+ } catch {
87
+ return '';
88
+ }
89
+ }
90
+
91
+ const MAX_LOG_BYTES = 5 * 1024 * 1024;
92
+
93
+ /** Keep one previous log so the file cannot grow without bound. */
94
+ function rotateLog() {
95
+ try {
96
+ if (fs.statSync(paths.log).size > MAX_LOG_BYTES) fs.renameSync(paths.log, `${paths.log}.1`);
97
+ } catch { /* no log yet */ }
98
+ }
99
+
100
+ async function ensureManager() {
101
+ const running = await health(baseUrl());
102
+ if (running) return { url: baseUrl(), started: false, version: running.version };
103
+
104
+ ensureDataDir();
105
+ rotateLog();
106
+ const log = fs.openSync(paths.log, 'a');
107
+ fs.writeSync(log, `\n--- starting manager ${new Date().toISOString()} ---\n`);
108
+ const child = spawn(process.execPath, [managerEntry], {
109
+ detached: true,
110
+ stdio: ['ignore', log, log],
111
+ windowsHide: true,
112
+ env: process.env,
113
+ });
114
+ child.unref();
115
+ fs.closeSync(log);
116
+
117
+ let exited = false;
118
+ child.once('exit', () => { exited = true; });
119
+ const deadline = Date.now() + 20000;
120
+ const expectedUrl = `http://${DEFAULT_HOST}:${resolvePort()}`;
121
+ while (Date.now() < deadline && !exited) {
122
+ await new Promise((r) => setTimeout(r, 250));
123
+ const url = readRuntimeFile()?.pid === child.pid ? readRuntimeFile().url : expectedUrl;
124
+ const up = await health(url, 500);
125
+ if (up) return { url, started: true, version: up.version };
126
+ }
127
+ // Two launchers started together both try to start a manager; the one
128
+ // that lost the race should use the winner rather than report a failure.
129
+ const winner = await health(expectedUrl, 1000);
130
+ if (winner) return { url: expectedUrl, started: false, version: winner.version };
131
+ const details = tailLog();
132
+ throw new Error(`the session manager did not start.${details ? `\n\nRecent log (${paths.log}):\n${details}` : ''}`);
133
+ }
134
+
135
+ async function cmdOpen({ browser }) {
136
+ const { url, started, version } = await ensureManager();
137
+ const token = loadOrCreateToken();
138
+ const target = pageUrl(url, token);
139
+ console.log(started ? `Session manager started at ${url}` : `Session manager already running at ${url}`);
140
+ const notice = versionNotice(version);
141
+ if (notice) console.log(notice);
142
+ if (browser) {
143
+ openBrowser(target);
144
+ console.log('Opening Agent Guild in your browser. You can close the page at any time; sessions keep running.');
145
+ } else {
146
+ console.log(`Open: ${target}`);
147
+ }
148
+ }
149
+
150
+ async function cmdStop() {
151
+ const url = baseUrl();
152
+ if (!(await health(url))) {
153
+ console.log('Session manager is not running.');
154
+ return;
155
+ }
156
+ // `stop` is documented as ending every session, so it does not ask; the
157
+ // web page's Stop manager button is the one that confirms first.
158
+ const res = await fetch(`${url}/api/v1/shutdown`, {
159
+ method: 'POST',
160
+ headers: { Authorization: `Bearer ${loadOrCreateToken()}`, 'Content-Type': 'application/json' },
161
+ body: JSON.stringify({ force: true }),
162
+ });
163
+ if (!res.ok) throw new Error(`stop failed: HTTP ${res.status}`);
164
+ const { running = 0 } = await res.json().catch(() => ({}));
165
+ if (running > 0) console.log(`Ending ${running} running session(s).`);
166
+ for (let i = 0; i < 40; i++) {
167
+ await new Promise((r) => setTimeout(r, 150));
168
+ if (!(await health(url, 300))) {
169
+ console.log('Session manager stopped.');
170
+ return;
171
+ }
172
+ }
173
+ console.log('Stop requested; the manager is still shutting down.');
174
+ }
175
+
176
+ async function cmdStatus() {
177
+ const url = baseUrl();
178
+ const h = await health(url);
179
+ if (!h) {
180
+ console.log('Session manager is not running.');
181
+ process.exitCode = 3;
182
+ return;
183
+ }
184
+ const res = await fetch(`${url}/api/v1/sessions`, { headers: { Authorization: `Bearer ${loadOrCreateToken()}` } });
185
+ const { sessions = [] } = res.ok ? await res.json() : {};
186
+ const running = sessions.filter((s) => s.status === 'running').length;
187
+ console.log(`Session manager ${h.version} running at ${url} (pid ${h.pid}).`);
188
+ const notice = versionNotice(h.version);
189
+ if (notice) console.log(notice);
190
+ console.log(`${sessions.length} session(s), ${running} running.`);
191
+ for (const s of sessions) {
192
+ const model = s.model ? ` [${s.model.displayName || s.model.name}]` : '';
193
+ const agents = s.agents.length ? `, ${s.agents.length} agent(s)` : '';
194
+ console.log(` ${s.id} ${s.provider.vendor.padEnd(10)} ${s.status.padEnd(8)} ${s.name}${model}${agents}`);
195
+ }
196
+ }
197
+
198
+ const MIN_NODE_MAJOR = 22;
199
+
200
+ async function main() {
201
+ const major = Number(process.versions.node.split('.')[0]);
202
+ if (major < MIN_NODE_MAJOR) {
203
+ throw new Error(`Node.js ${MIN_NODE_MAJOR} or newer is required; this is ${process.versions.node}. Install a current LTS from https://nodejs.org.`);
204
+ }
205
+ const args = process.argv.slice(2);
206
+ const flags = new Set(args.filter((a) => a.startsWith('-')));
207
+ const command = args.find((a) => !a.startsWith('-')) || 'open';
208
+ if (flags.has('-h') || flags.has('--help') || command === 'help') return usage();
209
+
210
+ switch (command) {
211
+ case 'open': return cmdOpen({ browser: !flags.has('--no-browser') });
212
+ case 'start': {
213
+ await import('../src/manager/main.mjs').then(async (m) => {
214
+ process.on('uncaughtException', (err) => console.error('[manager] unexpected error:', err));
215
+ process.on('unhandledRejection', (err) => console.error('[manager] unhandled rejection:', err));
216
+ const { shutdown } = await m.startManager();
217
+ console.log(`Open: ${pageUrl(readRuntimeFile()?.url ?? baseUrl(), loadOrCreateToken())}`);
218
+ for (const sig of ['SIGINT', 'SIGTERM', 'SIGHUP']) {
219
+ process.on(sig, () => shutdown(sig).then(() => process.exit(0)));
220
+ }
221
+ });
222
+ return undefined;
223
+ }
224
+ case 'stop': return cmdStop();
225
+ case 'status': return cmdStatus();
226
+ case 'url': {
227
+ console.log(pageUrl(baseUrl(), loadOrCreateToken()));
228
+ return undefined;
229
+ }
230
+ default:
231
+ usage();
232
+ process.exitCode = 2;
233
+ return undefined;
234
+ }
235
+ }
236
+
237
+ main().catch((err) => {
238
+ console.error(`agent-guild: ${err.message}`);
239
+ process.exit(1);
240
+ });