@noorm/marie-cli 0.1.17 → 0.1.25

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 (299) hide show
  1. package/README.md +7 -15
  2. package/SENTINEL.md +4 -7
  3. package/dist/cli-new/components/AgenticSpinner.js +28 -0
  4. package/dist/cli-new/components/AgenticSpinner.js.map +1 -0
  5. package/dist/cli-new/components/App.js +16 -63
  6. package/dist/cli-new/components/App.js.map +1 -1
  7. package/dist/cli-new/components/ApprovalDialog.js +3 -2
  8. package/dist/cli-new/components/ApprovalDialog.js.map +1 -1
  9. package/dist/cli-new/components/Banner.js +16 -5
  10. package/dist/cli-new/components/Banner.js.map +1 -1
  11. package/dist/cli-new/components/ChatArea.js +6 -7
  12. package/dist/cli-new/components/ChatArea.js.map +1 -1
  13. package/dist/cli-new/components/Header.js +14 -8
  14. package/dist/cli-new/components/Header.js.map +1 -1
  15. package/dist/cli-new/components/InputArea.js +98 -31
  16. package/dist/cli-new/components/InputArea.js.map +1 -1
  17. package/dist/cli-new/components/MessageBubble.js +28 -19
  18. package/dist/cli-new/components/MessageBubble.js.map +1 -1
  19. package/dist/cli-new/components/SessionSwitcher.js +6 -9
  20. package/dist/cli-new/components/SessionSwitcher.js.map +1 -1
  21. package/dist/cli-new/components/SetupWizard.js +80 -257
  22. package/dist/cli-new/components/SetupWizard.js.map +1 -1
  23. package/dist/cli-new/components/ToolCallDisplay.js +20 -5
  24. package/dist/cli-new/components/ToolCallDisplay.js.map +1 -1
  25. package/dist/cli-new/components/WizardSteps.js +22 -0
  26. package/dist/cli-new/components/WizardSteps.js.map +1 -0
  27. package/dist/cli-new/constants/SetupConstants.js +42 -0
  28. package/dist/cli-new/constants/SetupConstants.js.map +1 -0
  29. package/dist/cli-new/hooks/useGit.js +19 -62
  30. package/dist/cli-new/hooks/useGit.js.map +1 -1
  31. package/dist/cli-new/hooks/useMarie.js +26 -18
  32. package/dist/cli-new/hooks/useMarie.js.map +1 -1
  33. package/dist/cli-new/hooks/useSessions.js +1 -1
  34. package/dist/cli-new/hooks/useSessions.js.map +1 -1
  35. package/dist/cli-new/hooks/useSetupWizard.js +88 -0
  36. package/dist/cli-new/hooks/useSetupWizard.js.map +1 -0
  37. package/dist/cli-new/hooks/useUpdateCheck.js +4 -3
  38. package/dist/cli-new/hooks/useUpdateCheck.js.map +1 -1
  39. package/dist/cli-new/index.js +2 -4
  40. package/dist/cli-new/index.js.map +1 -1
  41. package/dist/cli-new/services/CommandService.js +104 -0
  42. package/dist/cli-new/services/CommandService.js.map +1 -0
  43. package/dist/cli-new/services/GitService.js +91 -0
  44. package/dist/cli-new/services/GitService.js.map +1 -0
  45. package/dist/cli-new/services/MarieService.js +77 -0
  46. package/dist/cli-new/services/MarieService.js.map +1 -0
  47. package/dist/cli-new/services/auth-server.js +128 -0
  48. package/dist/cli-new/services/auth-server.js.map +1 -0
  49. package/dist/cli-new/styles/theme.js +17 -17
  50. package/dist/cli-new/styles/theme.js.map +1 -1
  51. package/dist/cli-new/utils/version.js +24 -0
  52. package/dist/cli-new/utils/version.js.map +1 -0
  53. package/dist/monolith/adapters/CliMarieAdapter.js +19 -18
  54. package/dist/monolith/adapters/CliMarieAdapter.js.map +1 -1
  55. package/dist/monolith/cli/CliFileSystemPort.js +17 -3
  56. package/dist/monolith/cli/CliFileSystemPort.js.map +1 -1
  57. package/dist/monolith/cli/MarieToolDefinitionsCLI.js +44 -33
  58. package/dist/monolith/cli/MarieToolDefinitionsCLI.js.map +1 -1
  59. package/dist/monolith/cli/index.js +11 -20
  60. package/dist/monolith/cli/index.js.map +1 -1
  61. package/dist/monolith/cli/services/JoyAutomationServiceCLI.js +15 -62
  62. package/dist/monolith/cli/services/JoyAutomationServiceCLI.js.map +1 -1
  63. package/dist/monolith/cli/storage.js +154 -65
  64. package/dist/monolith/cli/storage.js.map +1 -1
  65. package/dist/monolith/domain/joy/RitualService.js +44 -46
  66. package/dist/monolith/domain/joy/RitualService.js.map +1 -1
  67. package/dist/monolith/domain/marie/MarieCortex.js +148 -0
  68. package/dist/monolith/domain/marie/MarieCortex.js.map +1 -0
  69. package/dist/monolith/domain/marie/PersonalityRenderer.js +97 -0
  70. package/dist/monolith/domain/marie/PersonalityRenderer.js.map +1 -0
  71. package/dist/monolith/infrastructure/Configuration.js +68 -0
  72. package/dist/monolith/infrastructure/Configuration.js.map +1 -0
  73. package/dist/monolith/infrastructure/CoreInfrastructure.js +204 -0
  74. package/dist/monolith/infrastructure/CoreInfrastructure.js.map +1 -0
  75. package/dist/monolith/infrastructure/ai/agents/MarieAscendant.js +3 -3
  76. package/dist/monolith/infrastructure/ai/agents/MarieAscendant.js.map +1 -1
  77. package/dist/monolith/infrastructure/ai/context/ContextArchiveService.js +51 -57
  78. package/dist/monolith/infrastructure/ai/context/ContextArchiveService.js.map +1 -1
  79. package/dist/monolith/infrastructure/ai/context/ContextManager.js +142 -98
  80. package/dist/monolith/infrastructure/ai/context/ContextManager.js.map +1 -1
  81. package/dist/monolith/infrastructure/ai/core/MarieEngine.js +104 -556
  82. package/dist/monolith/infrastructure/ai/core/MarieEngine.js.map +1 -1
  83. package/dist/monolith/infrastructure/ai/core/MarieEventDispatcher.js +1 -37
  84. package/dist/monolith/infrastructure/ai/core/MarieEventDispatcher.js.map +1 -1
  85. package/dist/monolith/infrastructure/ai/core/MarieLockManager.js +30 -5
  86. package/dist/monolith/infrastructure/ai/core/MarieLockManager.js.map +1 -1
  87. package/dist/monolith/infrastructure/ai/core/MarieProgressTracker.js +176 -196
  88. package/dist/monolith/infrastructure/ai/core/MarieProgressTracker.js.map +1 -1
  89. package/dist/monolith/infrastructure/ai/core/MariePulseService.js +41 -7
  90. package/dist/monolith/infrastructure/ai/core/MariePulseService.js.map +1 -1
  91. package/dist/monolith/infrastructure/ai/core/MarieSanitizer.js +303 -63
  92. package/dist/monolith/infrastructure/ai/core/MarieSanitizer.js.map +1 -1
  93. package/dist/monolith/infrastructure/ai/core/MarieSemaphore.js +47 -4
  94. package/dist/monolith/infrastructure/ai/core/MarieSemaphore.js.map +1 -1
  95. package/dist/monolith/infrastructure/ai/core/MarieSession.js +95 -15
  96. package/dist/monolith/infrastructure/ai/core/MarieSession.js.map +1 -1
  97. package/dist/monolith/infrastructure/ai/core/MarieStabilityMonitor.js +21 -0
  98. package/dist/monolith/infrastructure/ai/core/MarieStabilityMonitor.js.map +1 -1
  99. package/dist/monolith/infrastructure/ai/core/MarieToolMender.js +12 -0
  100. package/dist/monolith/infrastructure/ai/core/MarieToolMender.js.map +1 -1
  101. package/dist/monolith/infrastructure/ai/core/MarieToolProcessor.js +339 -481
  102. package/dist/monolith/infrastructure/ai/core/MarieToolProcessor.js.map +1 -1
  103. package/dist/monolith/infrastructure/ai/core/MarieVitality.js +238 -0
  104. package/dist/monolith/infrastructure/ai/core/MarieVitality.js.map +1 -0
  105. package/dist/monolith/infrastructure/ai/core/ReasoningBudget.js +23 -12
  106. package/dist/monolith/infrastructure/ai/core/ReasoningBudget.js.map +1 -1
  107. package/dist/monolith/infrastructure/ai/core/SessionLogService.js +9 -2
  108. package/dist/monolith/infrastructure/ai/core/SessionLogService.js.map +1 -1
  109. package/dist/monolith/infrastructure/ai/providers/AIProvider.js +402 -1
  110. package/dist/monolith/infrastructure/ai/providers/AIProvider.js.map +1 -1
  111. package/dist/monolith/infrastructure/ai/providers/DreamBeesProvider.js +114 -0
  112. package/dist/monolith/infrastructure/ai/providers/DreamBeesProvider.js.map +1 -0
  113. package/dist/monolith/infrastructure/ai/providers/OpenRouterProvider.js +426 -370
  114. package/dist/monolith/infrastructure/ai/providers/OpenRouterProvider.js.map +1 -1
  115. package/dist/monolith/infrastructure/ai/providers/OpenRouterStreamParser.js +235 -241
  116. package/dist/monolith/infrastructure/ai/providers/OpenRouterStreamParser.js.map +1 -1
  117. package/dist/monolith/infrastructure/ai/workerAi.js +185 -0
  118. package/dist/monolith/infrastructure/ai/workerAi.js.map +1 -0
  119. package/dist/monolith/infrastructure/config/ConfigService.js +216 -359
  120. package/dist/monolith/infrastructure/config/ConfigService.js.map +1 -1
  121. package/dist/monolith/infrastructure/joy/CognitiveRituals.js +8 -0
  122. package/dist/monolith/infrastructure/joy/CognitiveRituals.js.map +1 -0
  123. package/dist/monolith/infrastructure/joy/JoyTools.js +23 -43
  124. package/dist/monolith/infrastructure/joy/JoyTools.js.map +1 -1
  125. package/dist/monolith/infrastructure/persistence/MarieMindAutonomics.js +4 -0
  126. package/dist/monolith/infrastructure/persistence/MarieMindAutonomics.js.map +1 -0
  127. package/dist/monolith/infrastructure/persistence/MarieMindEngine.js +11 -0
  128. package/dist/monolith/infrastructure/persistence/MarieMindEngine.js.map +1 -0
  129. package/dist/monolith/infrastructure/persistence/NoormmeAutonomics.js +135 -0
  130. package/dist/monolith/infrastructure/persistence/NoormmeAutonomics.js.map +1 -0
  131. package/dist/monolith/infrastructure/persistence/NoormmeEngine.js +523 -0
  132. package/dist/monolith/infrastructure/persistence/NoormmeEngine.js.map +1 -0
  133. package/dist/monolith/infrastructure/persistence/NoormmeSchema.js +179 -0
  134. package/dist/monolith/infrastructure/persistence/NoormmeSchema.js.map +1 -0
  135. package/dist/monolith/infrastructure/persistence/NoormmeSeeder.js +94 -0
  136. package/dist/monolith/infrastructure/persistence/NoormmeSeeder.js.map +1 -0
  137. package/dist/monolith/infrastructure/persistence/NoormmeTools.js +371 -0
  138. package/dist/monolith/infrastructure/persistence/NoormmeTools.js.map +1 -0
  139. package/dist/monolith/infrastructure/services/MarieMemoryStore.js +133 -134
  140. package/dist/monolith/infrastructure/services/MarieMemoryStore.js.map +1 -1
  141. package/dist/monolith/infrastructure/tools/MarieToolDefinitions.js +6 -1578
  142. package/dist/monolith/infrastructure/tools/MarieToolDefinitions.js.map +1 -1
  143. package/dist/monolith/infrastructure/tools/PureStreamParser.js +68 -80
  144. package/dist/monolith/infrastructure/tools/PureStreamParser.js.map +1 -1
  145. package/dist/monolith/infrastructure/tools/SharedToolDefinitions.js +12 -11
  146. package/dist/monolith/infrastructure/tools/SharedToolDefinitions.js.map +1 -1
  147. package/dist/monolith/infrastructure/tools/SovereignTools.js +326 -0
  148. package/dist/monolith/infrastructure/tools/SovereignTools.js.map +1 -0
  149. package/dist/monolith/infrastructure/tools/ToolRegistry.js +45 -26
  150. package/dist/monolith/infrastructure/tools/ToolRegistry.js.map +1 -1
  151. package/dist/monolith/infrastructure/tools/definitions/AnalysisTools.js +232 -0
  152. package/dist/monolith/infrastructure/tools/definitions/AnalysisTools.js.map +1 -0
  153. package/dist/monolith/infrastructure/tools/definitions/AutomationTools.js +274 -0
  154. package/dist/monolith/infrastructure/tools/definitions/AutomationTools.js.map +1 -0
  155. package/dist/monolith/infrastructure/tools/definitions/ContextTools.js +71 -0
  156. package/dist/monolith/infrastructure/tools/definitions/ContextTools.js.map +1 -0
  157. package/dist/monolith/infrastructure/tools/definitions/CoreTools.js +37 -0
  158. package/dist/monolith/infrastructure/tools/definitions/CoreTools.js.map +1 -0
  159. package/dist/monolith/infrastructure/tools/definitions/DiagnosticTools.js +154 -0
  160. package/dist/monolith/infrastructure/tools/definitions/DiagnosticTools.js.map +1 -0
  161. package/dist/monolith/infrastructure/tools/definitions/NavigationTools.js +197 -0
  162. package/dist/monolith/infrastructure/tools/definitions/NavigationTools.js.map +1 -0
  163. package/dist/monolith/infrastructure/tools/definitions/PlanningTools.js +300 -0
  164. package/dist/monolith/infrastructure/tools/definitions/PlanningTools.js.map +1 -0
  165. package/dist/monolith/plumbing/Plumbing.js +238 -0
  166. package/dist/monolith/plumbing/Plumbing.js.map +1 -0
  167. package/dist/monolith/plumbing/PlumbingAnalysis.js +109 -0
  168. package/dist/monolith/plumbing/PlumbingAnalysis.js.map +1 -0
  169. package/dist/monolith/plumbing/PlumbingSystem.js +169 -0
  170. package/dist/monolith/plumbing/PlumbingSystem.js.map +1 -0
  171. package/dist/monolith/plumbing/analysis/ComplexityService.js +30 -34
  172. package/dist/monolith/plumbing/analysis/ComplexityService.js.map +1 -1
  173. package/dist/monolith/plumbing/analysis/DependencyService.js +55 -44
  174. package/dist/monolith/plumbing/analysis/DependencyService.js.map +1 -1
  175. package/dist/monolith/plumbing/analysis/DiscoveryService.js +40 -42
  176. package/dist/monolith/plumbing/analysis/DiscoveryService.js.map +1 -1
  177. package/dist/monolith/plumbing/analysis/JoyMapService.js +52 -56
  178. package/dist/monolith/plumbing/analysis/JoyMapService.js.map +1 -1
  179. package/dist/monolith/plumbing/analysis/LintService.js +118 -118
  180. package/dist/monolith/plumbing/analysis/LintService.js.map +1 -1
  181. package/dist/monolith/plumbing/analysis/MarieSentinelService.js +278 -269
  182. package/dist/monolith/plumbing/analysis/MarieSentinelService.js.map +1 -1
  183. package/dist/monolith/plumbing/analysis/QualityGuardrailService.js +116 -114
  184. package/dist/monolith/plumbing/analysis/QualityGuardrailService.js.map +1 -1
  185. package/dist/monolith/plumbing/analysis/SurgicalMender.js +57 -59
  186. package/dist/monolith/plumbing/analysis/SurgicalMender.js.map +1 -1
  187. package/dist/monolith/plumbing/analysis/TestService.js +89 -89
  188. package/dist/monolith/plumbing/analysis/TestService.js.map +1 -1
  189. package/dist/monolith/plumbing/filesystem/FileService.js +123 -195
  190. package/dist/monolith/plumbing/filesystem/FileService.js.map +1 -1
  191. package/dist/monolith/plumbing/filesystem/PathResolver.js +7 -8
  192. package/dist/monolith/plumbing/filesystem/PathResolver.js.map +1 -1
  193. package/dist/monolith/plumbing/git/GitService.js +4 -4
  194. package/dist/monolith/plumbing/git/GitService.js.map +1 -1
  195. package/dist/monolith/plumbing/lsp/SymbolService.js +5 -34
  196. package/dist/monolith/plumbing/lsp/SymbolService.js.map +1 -1
  197. package/dist/monolith/plumbing/terminal/ProcessRegistry.js +20 -22
  198. package/dist/monolith/plumbing/terminal/ProcessRegistry.js.map +1 -1
  199. package/dist/monolith/plumbing/terminal/TerminalService.js +127 -136
  200. package/dist/monolith/plumbing/terminal/TerminalService.js.map +1 -1
  201. package/dist/monolith/plumbing/utils/EnvironmentUtils.js +3 -23
  202. package/dist/monolith/plumbing/utils/EnvironmentUtils.js.map +1 -1
  203. package/dist/monolith/plumbing/utils/JsonUtils.js +252 -311
  204. package/dist/monolith/plumbing/utils/JsonUtils.js.map +1 -1
  205. package/dist/monolith/plumbing/utils/MutexUtils.js.map +1 -1
  206. package/dist/monolith/plumbing/utils/PlumbingCore.js +549 -0
  207. package/dist/monolith/plumbing/utils/PlumbingCore.js.map +1 -0
  208. package/dist/monolith/plumbing/utils/PrefixTree.js +61 -114
  209. package/dist/monolith/plumbing/utils/PrefixTree.js.map +1 -1
  210. package/dist/monolith/plumbing/utils/StreamTagDetector.js +89 -127
  211. package/dist/monolith/plumbing/utils/StreamTagDetector.js.map +1 -1
  212. package/dist/monolith/plumbing/utils/StringUtils.js +87 -89
  213. package/dist/monolith/plumbing/utils/StringUtils.js.map +1 -1
  214. package/dist/monolith/runtime/MarieRuntime.js +76 -417
  215. package/dist/monolith/runtime/MarieRuntime.js.map +1 -1
  216. package/dist/monolith/runtime/RuntimeAdapterBase.js +1 -1
  217. package/dist/monolith/runtime/RuntimeAdapterBase.js.map +1 -1
  218. package/dist/monolith/runtime/providerFactory.js +1 -7
  219. package/dist/monolith/runtime/providerFactory.js.map +1 -1
  220. package/dist/monolith/services/HealthService.js +29 -32
  221. package/dist/monolith/services/HealthService.js.map +1 -1
  222. package/dist/monolith/services/JoyAutomationService.js +58 -95
  223. package/dist/monolith/services/JoyAutomationService.js.map +1 -1
  224. package/dist/monolith/services/MarieAutomationService.js +59 -0
  225. package/dist/monolith/services/MarieAutomationService.js.map +1 -0
  226. package/dist/monolith/services/MarieGhostService.js +46 -161
  227. package/dist/monolith/services/MarieGhostService.js.map +1 -1
  228. package/dist/monolith/services/MarieServices.js +102 -0
  229. package/dist/monolith/services/MarieServices.js.map +1 -0
  230. package/dist/monolith/services/MarieTypes.js +2 -0
  231. package/dist/monolith/services/MarieTypes.js.map +1 -0
  232. package/dist/monolith/services/UpdateService.js +47 -49
  233. package/dist/monolith/services/UpdateService.js.map +1 -1
  234. package/dist/prompts.js +11 -5
  235. package/dist/prompts.js.map +1 -1
  236. package/dist/test_prefix_tree.js +9 -9
  237. package/dist/test_prefix_tree.js.map +1 -1
  238. package/package.json +18 -88
  239. package/run_test.js +5 -0
  240. package/.marie_visual_verify_1771225696548/progress_bar_check.txt +0 -1
  241. package/dist/extension.cjs +0 -635
  242. package/dist/extension.js +0 -473
  243. package/dist/extension.js.map +0 -1
  244. package/dist/monolith/adapters/VscodeMarieAdapter.js +0 -81
  245. package/dist/monolith/adapters/VscodeMarieAdapter.js.map +0 -1
  246. package/dist/monolith/domain/joy/JoyTools.js +0 -535
  247. package/dist/monolith/domain/joy/JoyTools.js.map +0 -1
  248. package/dist/monolith/infrastructure/ai/agents/MarieYOLO.js +0 -207
  249. package/dist/monolith/infrastructure/ai/agents/MarieYOLO.js.map +0 -1
  250. package/dist/monolith/infrastructure/ai/core/GhostPort.js +0 -2
  251. package/dist/monolith/infrastructure/ai/core/GhostPort.js.map +0 -1
  252. package/dist/monolith/infrastructure/ai/core/MarieYOLOTypes.js +0 -2
  253. package/dist/monolith/infrastructure/ai/core/MarieYOLOTypes.js.map +0 -1
  254. package/dist/monolith/infrastructure/ai/core/VscodeFileSystemPort.js +0 -33
  255. package/dist/monolith/infrastructure/ai/core/VscodeFileSystemPort.js.map +0 -1
  256. package/dist/monolith/infrastructure/ai/providers/AnthropicProvider.js +0 -148
  257. package/dist/monolith/infrastructure/ai/providers/AnthropicProvider.js.map +0 -1
  258. package/dist/monolith/infrastructure/ai/providers/CerebrasProvider.js +0 -208
  259. package/dist/monolith/infrastructure/ai/providers/CerebrasProvider.js.map +0 -1
  260. package/dist/monolith/plumbing/ui/DecorationService.js +0 -54
  261. package/dist/monolith/plumbing/ui/DecorationService.js.map +0 -1
  262. package/dist/monolith/services/JoyLogService.js +0 -48
  263. package/dist/monolith/services/JoyLogService.js.map +0 -1
  264. package/dist/monolith/services/JoyService.js +0 -209
  265. package/dist/monolith/services/JoyService.js.map +0 -1
  266. package/dist/monolith/services/MarieSCMProvider.js +0 -41
  267. package/dist/monolith/services/MarieSCMProvider.js.map +0 -1
  268. package/dist/test_agent_stream_control_plane.js +0 -170
  269. package/dist/test_agent_stream_control_plane.js.map +0 -1
  270. package/dist/test_strategy_integration.js +0 -114
  271. package/dist/test_strategy_integration.js.map +0 -1
  272. package/dist/test_streaming_fragility.js +0 -191
  273. package/dist/test_streaming_fragility.js.map +0 -1
  274. package/dist/webview-ui/App.js +0 -16
  275. package/dist/webview-ui/App.js.map +0 -1
  276. package/dist/webview-ui/Providers.js +0 -6
  277. package/dist/webview-ui/Providers.js.map +0 -1
  278. package/dist/webview-ui/components/ApprovalPanel.js +0 -8
  279. package/dist/webview-ui/components/ApprovalPanel.js.map +0 -1
  280. package/dist/webview-ui/components/ChatPanel.js +0 -19
  281. package/dist/webview-ui/components/ChatPanel.js.map +0 -1
  282. package/dist/webview-ui/components/Composer.js +0 -19
  283. package/dist/webview-ui/components/Composer.js.map +0 -1
  284. package/dist/webview-ui/components/HeaderBar.js +0 -5
  285. package/dist/webview-ui/components/HeaderBar.js.map +0 -1
  286. package/dist/webview-ui/components/SessionList.js +0 -14
  287. package/dist/webview-ui/components/SessionList.js.map +0 -1
  288. package/dist/webview-ui/context/WebviewStateContext.js +0 -146
  289. package/dist/webview-ui/context/WebviewStateContext.js.map +0 -1
  290. package/dist/webview-ui/main.css +0 -1
  291. package/dist/webview-ui/main.js +0 -108
  292. package/dist/webview-ui/main.js.map +0 -1
  293. package/dist/webview-ui/types.js +0 -2
  294. package/dist/webview-ui/types.js.map +0 -1
  295. package/dist/webview-ui/vscode.js +0 -4
  296. package/dist/webview-ui/vscode.js.map +0 -1
  297. package/lint_output.txt +0 -705
  298. package/lint_output_v2.txt +0 -711
  299. package/marie-coder-0.1.16.vsix +0 -0
@@ -1,22 +1,15 @@
1
- import { StringUtils } from "./StringUtils.js";
1
+ import { levenshtein } from "./StringUtils.js";
2
+ const MAX_CACHE_SIZE = 1000;
2
3
  /**
3
- * Prefix Tree (Trie) for efficient tag detection.
4
+ * Creates a Prefix Tree (Trie) for efficient tag detection.
4
5
  * Provides O(k) complexity for finding tags where k = input length.
5
6
  */
6
- export class PrefixTree {
7
- root = { children: new Map(), isEndOfTag: false };
8
- tags = [];
9
- constructor(tags) {
10
- this.tags = tags;
11
- for (const tag of tags) {
12
- this.insert(tag);
13
- }
14
- }
15
- /**
16
- * Insert a tag into the trie.
17
- */
18
- insert(tag) {
19
- let node = this.root;
7
+ export function createPrefixTree(tags) {
8
+ const root = { children: new Map(), isEndOfTag: false };
9
+ const editDistanceCache = new Map();
10
+ // Initialize
11
+ for (const tag of tags) {
12
+ let node = root;
20
13
  for (const char of tag) {
21
14
  if (!node.children.has(char)) {
22
15
  node.children.set(char, { children: new Map(), isEndOfTag: false });
@@ -26,128 +19,82 @@ export class PrefixTree {
26
19
  node.isEndOfTag = true;
27
20
  node.tag = tag;
28
21
  }
29
- /**
30
- * Find the earliest complete tag in the text.
31
- * Returns { index: number, tag: string } if found, null otherwise.
32
- * Optimized with early-exit for O(k) performance.
33
- */
34
- findEarliestTag(text) {
35
- let earliestIndex = Infinity;
36
- let earliestTag = "";
37
- // Try to match from each position in the text (with early-exit)
38
- for (let startIdx = 0; startIdx < text.length; startIdx++) {
39
- // Early-exit: if we already found a tag at an earlier position, stop
40
- if (startIdx >= earliestIndex) {
41
- break;
42
- }
43
- const result = this.matchFromPosition(text, startIdx);
44
- if (result && result.index < earliestIndex) {
45
- earliestIndex = result.index;
46
- earliestTag = result.tag;
47
- }
48
- }
49
- return earliestTag ? { index: earliestIndex, tag: earliestTag } : null;
50
- }
51
- /**
52
- * Match a tag starting from a specific position.
53
- * Returns the SHORTEST matching tag (to handle prefix overlaps correctly).
54
- */
55
- matchFromPosition(text, startIdx) {
56
- let node = this.root;
22
+ function matchFromPosition(text, startIdx) {
23
+ let node = root;
57
24
  let firstMatch = null;
58
25
  for (let i = startIdx; i < text.length; i++) {
59
26
  const char = text[i];
60
- if (!node.children.has(char)) {
61
- // Can't continue matching
27
+ if (!node.children.has(char))
62
28
  break;
63
- }
64
29
  node = node.children.get(char);
65
30
  if (node.isEndOfTag && !firstMatch) {
66
- // Found first complete tag at this position
67
31
  firstMatch = node.tag;
68
- // Return immediately to get the shortest match
69
32
  return { index: startIdx, tag: firstMatch };
70
33
  }
71
34
  }
72
35
  return null;
73
36
  }
74
- /**
75
- * Find the longest partial tag at the end of the text.
76
- * Returns the length of the partial match (0 if none).
77
- */
78
- findLongestPartialAtEnd(text) {
79
- let maxPartialLength = 0;
80
- // Try matching from each position toward the end
81
- for (let startIdx = 0; startIdx < text.length; startIdx++) {
82
- const partialLength = this.matchPartialFromPosition(text, startIdx);
83
- if (partialLength > 0 && startIdx + partialLength === text.length) {
84
- maxPartialLength = Math.max(maxPartialLength, partialLength);
85
- }
86
- }
87
- return maxPartialLength;
88
- }
89
- /**
90
- * Match a partial tag from a position, returns length of match.
91
- */
92
- matchPartialFromPosition(text, startIdx) {
93
- let node = this.root;
37
+ function matchPartialFromPosition(text, startIdx) {
38
+ let node = root;
94
39
  let matchLength = 0;
95
40
  for (let i = startIdx; i < text.length; i++) {
96
41
  const char = text[i];
97
- if (!node.children.has(char)) {
42
+ if (!node.children.has(char))
98
43
  return matchLength;
99
- }
100
44
  node = node.children.get(char);
101
45
  matchLength++;
102
- if (node.isEndOfTag) {
103
- // This is a complete tag, not a partial
46
+ if (node.isEndOfTag)
104
47
  return 0;
105
- }
106
48
  }
107
- // We matched up to the end of text without completing a tag
108
49
  return matchLength;
109
50
  }
110
- editDistanceCache = new Map();
111
- static MAX_CACHE_SIZE = 1000;
112
- /**
113
- * Find similar tags using edit distance (Levenshtein).
114
- * Returns tags with edit distance <= maxDistance.
115
- * Uses caching with eviction for improved performance.
116
- */
117
- findSimilarTags(input, maxDistance = 2) {
118
- const similar = [];
119
- for (const tag of this.tags) {
120
- const cacheKey = `${input}:${tag}`;
121
- let distance = this.editDistanceCache.get(cacheKey);
122
- if (distance === undefined) {
123
- distance = this.editDistance(input, tag);
124
- // Evict oldest half when cache exceeds max size
125
- if (this.editDistanceCache.size >= PrefixTree.MAX_CACHE_SIZE) {
126
- const keysToDelete = Array.from(this.editDistanceCache.keys()).slice(0, PrefixTree.MAX_CACHE_SIZE / 2);
127
- for (const key of keysToDelete) {
128
- this.editDistanceCache.delete(key);
129
- }
51
+ return {
52
+ findEarliestTag(text) {
53
+ let earliestIndex = Infinity;
54
+ let earliestTag = "";
55
+ for (let startIdx = 0; startIdx < text.length; startIdx++) {
56
+ if (startIdx >= earliestIndex)
57
+ break;
58
+ const result = matchFromPosition(text, startIdx);
59
+ if (result && result.index < earliestIndex) {
60
+ earliestIndex = result.index;
61
+ earliestTag = result.tag;
130
62
  }
131
- this.editDistanceCache.set(cacheKey, distance);
132
63
  }
133
- if (distance <= maxDistance) {
134
- similar.push(tag);
64
+ return earliestTag ? { index: earliestIndex, tag: earliestTag } : null;
65
+ },
66
+ findLongestPartialAtEnd(text) {
67
+ let maxPartialLength = 0;
68
+ for (let startIdx = 0; startIdx < text.length; startIdx++) {
69
+ const partialLength = matchPartialFromPosition(text, startIdx);
70
+ if (partialLength > 0 && startIdx + partialLength === text.length) {
71
+ maxPartialLength = Math.max(maxPartialLength, partialLength);
72
+ }
135
73
  }
136
- }
137
- return similar;
138
- }
139
- /**
140
- * Calculate Levenshtein edit distance between two strings.
141
- * Delegates to StringUtils for the optimized 2-row implementation.
142
- */
143
- editDistance(a, b) {
144
- return StringUtils.levenshtein(a, b);
145
- }
146
- /**
147
- * Clear the edit distance cache to free memory.
148
- */
149
- clearCache() {
150
- this.editDistanceCache.clear();
151
- }
74
+ return maxPartialLength;
75
+ },
76
+ findSimilarTags(input, maxDistance = 2) {
77
+ const similar = [];
78
+ for (const tag of tags) {
79
+ const cacheKey = `${input}:${tag}`;
80
+ let distance = editDistanceCache.get(cacheKey);
81
+ if (distance === undefined) {
82
+ distance = levenshtein(input, tag);
83
+ if (editDistanceCache.size >= MAX_CACHE_SIZE) {
84
+ const keysToDelete = Array.from(editDistanceCache.keys()).slice(0, MAX_CACHE_SIZE / 2);
85
+ for (const key of keysToDelete)
86
+ editDistanceCache.delete(key);
87
+ }
88
+ editDistanceCache.set(cacheKey, distance);
89
+ }
90
+ if (distance <= maxDistance)
91
+ similar.push(tag);
92
+ }
93
+ return similar;
94
+ },
95
+ clearCache() {
96
+ editDistanceCache.clear();
97
+ },
98
+ };
152
99
  }
153
100
  //# sourceMappingURL=PrefixTree.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"PrefixTree.js","sourceRoot":"","sources":["../../../../src/monolith/plumbing/utils/PrefixTree.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"PrefixTree.js","sourceRoot":"","sources":["../../../../src/monolith/plumbing/utils/PrefixTree.ts"],"names":[],"mappings":"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"}
@@ -1,130 +1,92 @@
1
- import { PrefixTree } from "./PrefixTree.js";
2
- export class StreamTagDetector {
3
- buffer = "";
4
- static MAX_BUFFER_SIZE = 100000; // 100k chars safety limit
5
- // Tags we want to detect.
6
- // We strictly look for the start of a tool block or the end of one.
7
- // Also includes Llama 3 variations and control tokens.
8
- tags = [
9
- "<|tool_call_begin|>",
10
- "<|tool_call_end|>",
11
- "<|tool_calls_section_begin|>", // Section begin marker
12
- "<|tool_calls_section_end|>", // Section end marker
13
- "<|tool_call_id|>", // Some models emit tool IDs separately
14
- "<|tool_call_argument_begin|>",
15
- "<|tool_call_arguments_begin|>", // Plural variant
16
- "<tool>",
17
- "</tool>",
18
- "<function",
19
- "</function>",
20
- "<function_calls>",
21
- "</function_calls>",
22
- "<invoke",
23
- "</invoke>",
24
- "<thought>",
25
- "</thought>",
26
- "<tool_code>",
27
- "</tool_code>",
28
- "<tool_call>",
29
- "</tool_call>",
30
- "<|eot_id|>", // End of turn marker
31
- "<|start_header_id|>", // Header start marker
32
- "<|end_header_id|>", // Header end marker
33
- ];
34
- prefixTree;
35
- constructor() {
36
- this.prefixTree = new PrefixTree(this.tags);
37
- }
38
- /**
39
- * Processes a chunk of text and returns a status indicating what happened.
40
- *
41
- * - 'tag': A full tag was found. The returned `text` is content BEFORE the tag. `tag` is the tag itself.
42
- * The buffer will contain any remainder AFTER the tag for the next call.
43
- * - 'incomplete': A partial tag was found at the end. `text` is the safe content before it.
44
- * The buffer holds the partial tag.
45
- * - 'content': No tags found. `text` Is the full content. Buffer is empty.
46
- */
47
- process(chunk) {
48
- this.buffer += chunk;
49
- // --- Buffer Growth Safety ---
50
- if (this.buffer.length > StreamTagDetector.MAX_BUFFER_SIZE) {
51
- console.error("[Marie] StreamTagDetector buffer exceeded safety limit. Flushing.");
52
- const flushed = this.buffer;
53
- this.buffer = "";
54
- return { type: "content", text: flushed };
55
- }
56
- // 1. Check if we have any FULL tags using prefix tree (O(k) complexity)
57
- const tagMatch = this.prefixTree.findEarliestTag(this.buffer);
58
- if (tagMatch) {
59
- // Found a tag!
60
- // Emit content up to tag
61
- const content = this.buffer.substring(0, tagMatch.index);
62
- // Remove content + tag from buffer, keep remainder
63
- this.buffer = this.buffer.substring(tagMatch.index + tagMatch.tag.length);
64
- console.log(`[Marie] Tag detected: ${tagMatch.tag} at index ${tagMatch.index}`);
65
- return { type: "tag", text: content, tag: tagMatch.tag };
66
- }
67
- // 2. Check for dynamic/malformed tags using regex
68
- const lookbackLength = Math.min(200, this.buffer.length);
69
- const recentBuffer = this.buffer.substring(this.buffer.length - lookbackLength);
70
- // IMPORTANT: Keep this strict to avoid treating normal HTML/text tags
71
- // (e.g. <script>, </button>) as tool tags.
72
- // We only accept:
73
- // - LLM control tags like <|tool_call_begin|>
74
- // - compact call markers like call:0>
75
- // - bracketed tool markers like [Tool Use: name]
76
- const dynamicTagPattern = /<\|[\w_]{3,}(?:\|>|>)?|(?:^|[^a-zA-Z0-9_])(call:\d+>)|(?:^|[\s,])(\[Tool (?:Use|Result):[^\]]+\])/g;
77
- const matches = Array.from(recentBuffer.matchAll(dynamicTagPattern));
78
- if (matches.length > 0) {
79
- const lastMatch = matches[matches.length - 1];
80
- // If we have a capture group (index 1 or 2), use it, otherwise use the full match
81
- const potentialTag = lastMatch[2] || lastMatch[1] || lastMatch[0];
82
- // If it's a perfect match for a known tag or matches our dynamic pattern
83
- // If we used a capture group, we need to adjust the index to point to that group specifically
84
- const matchIndex = this.buffer.length -
85
- lookbackLength +
86
- lastMatch.index +
87
- (lastMatch[0].length - potentialTag.length);
88
- // Check if this is a definite tag (ends with > or ] or is a known tag)
89
- if (potentialTag.endsWith(">") ||
90
- potentialTag.endsWith("]") ||
91
- this.tags.includes(potentialTag)) {
92
- const content = this.buffer.substring(0, matchIndex);
93
- this.buffer = this.buffer.substring(matchIndex + potentialTag.length);
94
- console.log(`[Marie] Dynamic tag detected: ${potentialTag}`);
95
- return { type: "tag", text: content, tag: potentialTag };
1
+ import { createPrefixTree } from "./PrefixTree.js";
2
+ const MAX_BUFFER_SIZE = 100000; // 100k chars safety limit
3
+ // Tags we want to detect.
4
+ const DEFAULT_TAGS = [
5
+ "<|tool_call_begin|>",
6
+ "<|tool_call_end|>",
7
+ "<|tool_calls_section_begin|>", // Section begin marker
8
+ "<|tool_calls_section_end|>", // Section end marker
9
+ "<|tool_call_id|>", // Some models emit tool IDs separately
10
+ "<|tool_call_argument_begin|>",
11
+ "<|tool_call_arguments_begin|>", // Plural variant
12
+ "<tool>",
13
+ "</tool>",
14
+ "<function",
15
+ "</function>",
16
+ "<function_calls>",
17
+ "</function_calls>",
18
+ "<invoke",
19
+ "</invoke>",
20
+ "<thought>",
21
+ "</thought>",
22
+ "<tool_code>",
23
+ "</tool_code>",
24
+ "<tool_call>",
25
+ "</tool_call>",
26
+ "<|eot_id|>", // End of turn marker
27
+ "<|start_header_id|>", // Header start marker
28
+ "<|end_header_id|>", // Header end marker
29
+ ];
30
+ export function createStreamTagDetector() {
31
+ let buffer = "";
32
+ const prefixTree = createPrefixTree(DEFAULT_TAGS);
33
+ return {
34
+ process(chunk) {
35
+ buffer += chunk;
36
+ if (buffer.length > MAX_BUFFER_SIZE) {
37
+ console.error("[Marie] StreamTagDetector buffer exceeded safety limit. Flushing.");
38
+ const flushed = buffer;
39
+ buffer = "";
40
+ return { type: "content", text: flushed };
96
41
  }
97
- }
98
- // 3. Check for partials (both prefix tree and dynamic)
99
- const partialLength = this.prefixTree.findLongestPartialAtEnd(this.buffer);
100
- // Dynamic partial check (strict): only hold potential control-tag prefixes,
101
- // not generic trailing words/text.
102
- const trailingControlTag = this.buffer.match(/<\|[\w_]*$/);
103
- const trailingCallMarker = this.buffer.match(/call:\d*$/);
104
- const dynamicPartialLength = Math.max(trailingControlTag ? trailingControlTag[0].length : 0, trailingCallMarker ? trailingCallMarker[0].length : 0);
105
- const maxPartial = Math.max(partialLength, dynamicPartialLength);
106
- if (maxPartial > 0) {
107
- const unsafeStart = this.buffer.length - maxPartial;
108
- const content = this.buffer.substring(0, unsafeStart);
109
- this.buffer = this.buffer.substring(unsafeStart);
110
- return { type: "incomplete", text: content };
111
- }
112
- // 4. No tags, no partials. Emit all.
113
- const allContent = this.buffer;
114
- this.buffer = "";
115
- return { type: "content", text: allContent };
116
- }
117
- /**
118
- * Resets the internal buffer. Useful for cleanup between sessions.
119
- */
120
- reset() {
121
- this.buffer = "";
122
- }
123
- /**
124
- * Returns the current buffer size for monitoring.
125
- */
126
- getBufferSize() {
127
- return this.buffer.length;
128
- }
42
+ const tagMatch = prefixTree.findEarliestTag(buffer);
43
+ if (tagMatch) {
44
+ const content = buffer.substring(0, tagMatch.index);
45
+ buffer = buffer.substring(tagMatch.index + tagMatch.tag.length);
46
+ console.log(`[Marie] Tag detected: ${tagMatch.tag} at index ${tagMatch.index}`);
47
+ return { type: "tag", text: content, tag: tagMatch.tag };
48
+ }
49
+ const lookbackLength = Math.min(200, buffer.length);
50
+ const recentBuffer = buffer.substring(buffer.length - lookbackLength);
51
+ const dynamicTagPattern = /<\|[\w_]{3,}(?:\|>|>)?|(?:^|[^a-zA-Z0-9_])(call:\d+>)|(?:^|[\s,])(\[Tool (?:Use|Result):[^\]]+\])/g;
52
+ const matches = Array.from(recentBuffer.matchAll(dynamicTagPattern));
53
+ if (matches.length > 0) {
54
+ const lastMatch = matches[matches.length - 1];
55
+ const potentialTag = lastMatch[2] || lastMatch[1] || lastMatch[0];
56
+ const matchIndex = buffer.length -
57
+ lookbackLength +
58
+ lastMatch.index +
59
+ (lastMatch[0].length - potentialTag.length);
60
+ if (potentialTag.endsWith(">") ||
61
+ potentialTag.endsWith("]") ||
62
+ DEFAULT_TAGS.includes(potentialTag)) {
63
+ const content = buffer.substring(0, matchIndex);
64
+ buffer = buffer.substring(matchIndex + potentialTag.length);
65
+ console.log(`[Marie] Dynamic tag detected: ${potentialTag}`);
66
+ return { type: "tag", text: content, tag: potentialTag };
67
+ }
68
+ }
69
+ const partialLength = prefixTree.findLongestPartialAtEnd(buffer);
70
+ const trailingControlTag = buffer.match(/<\|[\w_]*$/);
71
+ const trailingCallMarker = buffer.match(/call:\d*$/);
72
+ const dynamicPartialLength = Math.max(trailingControlTag ? trailingControlTag[0].length : 0, trailingCallMarker ? trailingCallMarker[0].length : 0);
73
+ const maxPartial = Math.max(partialLength, dynamicPartialLength);
74
+ if (maxPartial > 0) {
75
+ const unsafeStart = buffer.length - maxPartial;
76
+ const content = buffer.substring(0, unsafeStart);
77
+ buffer = buffer.substring(unsafeStart);
78
+ return { type: "incomplete", text: content };
79
+ }
80
+ const allContent = buffer;
81
+ buffer = "";
82
+ return { type: "content", text: allContent };
83
+ },
84
+ reset() {
85
+ buffer = "";
86
+ },
87
+ getBufferSize() {
88
+ return buffer.length;
89
+ },
90
+ };
129
91
  }
130
92
  //# sourceMappingURL=StreamTagDetector.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"StreamTagDetector.js","sourceRoot":"","sources":["../../../../src/monolith/plumbing/utils/StreamTagDetector.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"StreamTagDetector.js","sourceRoot":"","sources":["../../../../src/monolith/plumbing/utils/StreamTagDetector.ts"],"names":[],"mappings":"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"}