@tyvm/knowhow 0.0.32 → 0.0.34

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 (508) hide show
  1. package/autodoc/plugins/downloader/downloader.mdx +2 -2
  2. package/benchmarks/.dockerignore +7 -0
  3. package/benchmarks/README.md +166 -0
  4. package/benchmarks/docker/Dockerfile +68 -0
  5. package/benchmarks/example-config.yml +27 -0
  6. package/benchmarks/jest.config.js +13 -0
  7. package/benchmarks/package-lock.json +4297 -0
  8. package/benchmarks/package.json +39 -0
  9. package/benchmarks/results/4542435/2025-08-05/lms/lms-openai-gpt-oss-20b.json +2814 -0
  10. package/benchmarks/results/4542435/2025-08-05/lms/lms-qwen-qwen3-30b-a3b-2507.json +2014 -0
  11. package/benchmarks/results/4fb9125/2025-08-07/anthropic/anthropic-claude-sonnet-4-20250514.json +3121 -0
  12. package/benchmarks/results/5766aee/2025-08-02/lms-qwen/qwen3-coder-30b.json +98 -0
  13. package/benchmarks/results/6d73808/2025-08-07/openai/openai-gpt-5.json +3256 -0
  14. package/benchmarks/results/77bf0a6/2025-08-02/lms-qwen/qwen3-30b-a3b-2507.json +4298 -0
  15. package/benchmarks/results/8c0d445/2025-08-03/anthropic/anthropic-claude-sonnet-4-20250514.json +3031 -0
  16. package/benchmarks/results/8c0d445/2025-08-03/openai/openai-gpt-4.1-2025-04-14.json +2990 -0
  17. package/benchmarks/results/ac6b2ab/2025-08-03/anthropic/anthropic-claude-sonnet-4-20250514.json +3256 -0
  18. package/benchmarks/results/ac6b2ab/2025-08-03/lms/lms-qwen-qwen3-coder-30b.json +3007 -0
  19. package/benchmarks/results/ac6b2ab/2025-08-03/openai/openai-gpt-4.1-2025-04-14.json +3256 -0
  20. package/benchmarks/results/ac6b2ab/2025-08-03/openai/openai-gpt-4.1-mini-2025-04-14.json +3036 -0
  21. package/benchmarks/results/ac6b2ab/2025-08-03/openai/openai-gpt-4.1-nano-2025-04-14.json +3280 -0
  22. package/benchmarks/results/adff675/2025-08-04/lms/lms-qwen-qwen3-30b-a3b-2507.json +1920 -0
  23. package/benchmarks/results/adff675/2025-08-04/lms/lms-qwen-qwen3-coder-30b.json +3281 -0
  24. package/benchmarks/results/b502ed9/2025-08-03/lms-qwen/qwen3-coder-30b.json +2896 -0
  25. package/benchmarks/results/d1a8129/2025-08-03/lms/lms-qwen-qwen3-coder-30b.json +3011 -0
  26. package/benchmarks/results/e60471c/2025-08-03/lms/qwen3-30b-a3b-2507.json +3003 -0
  27. package/benchmarks/scripts/build-and-run.sh +47 -0
  28. package/benchmarks/scripts/clone-exercism.sh +92 -0
  29. package/benchmarks/scripts/validate.sh +48 -0
  30. package/benchmarks/src/__tests__/runner.test.ts +27 -0
  31. package/benchmarks/src/cli.ts +90 -0
  32. package/benchmarks/src/evaluators/EvaluatorRegistry.ts +64 -0
  33. package/benchmarks/src/evaluators/JavaScriptEvaluator.ts +183 -0
  34. package/benchmarks/src/evaluators/index.ts +3 -0
  35. package/benchmarks/src/evaluators/types.ts +22 -0
  36. package/benchmarks/src/index.ts +3 -0
  37. package/benchmarks/src/providers.ts +13 -0
  38. package/benchmarks/src/runner.ts +824 -0
  39. package/benchmarks/src/types.ts +63 -0
  40. package/benchmarks/tsconfig.json +19 -0
  41. package/jest.config.js +2 -1
  42. package/leaderboard/README.md +148 -0
  43. package/leaderboard/app/api/benchmark-data/route.ts +131 -0
  44. package/leaderboard/app/api/benchmark-detail/route.ts +172 -0
  45. package/leaderboard/app/details/[model]/[provider]/[language]/page.tsx +501 -0
  46. package/leaderboard/app/exercise/[model]/[provider]/[language]/[exercise]/page.tsx +375 -0
  47. package/leaderboard/app/globals.css +27 -0
  48. package/leaderboard/app/layout.tsx +21 -0
  49. package/leaderboard/app/page.tsx +170 -0
  50. package/leaderboard/components/LeaderboardTable.tsx +168 -0
  51. package/leaderboard/components/PerformanceChart.tsx +109 -0
  52. package/leaderboard/next-env.d.ts +5 -0
  53. package/leaderboard/next.config.js +4 -0
  54. package/leaderboard/package-lock.json +6363 -0
  55. package/leaderboard/package.json +28 -0
  56. package/leaderboard/postcss.config.js +6 -0
  57. package/leaderboard/tailwind.config.js +17 -0
  58. package/leaderboard/tsconfig.json +28 -0
  59. package/leaderboard/types/benchmark.ts +67 -0
  60. package/leaderboard/utils/dataProcessor.ts +33 -0
  61. package/package.json +2 -1
  62. package/src/agents/base/base.ts +147 -21
  63. package/src/agents/base/prompt.ts +28 -0
  64. package/src/agents/index.ts +3 -0
  65. package/src/agents/patcher/patcher.ts +6 -4
  66. package/src/agents/setup/setup.ts +56 -0
  67. package/src/agents/tools/agentCall.ts +6 -2
  68. package/src/agents/tools/aiClient.ts +74 -8
  69. package/src/agents/tools/execCommand.ts +13 -14
  70. package/src/agents/tools/executeScript/README.md +16 -0
  71. package/src/agents/tools/index.ts +2 -0
  72. package/src/agents/tools/list.ts +73 -16
  73. package/src/agents/tools/startAgentTask.ts +109 -0
  74. package/src/agents/tools/textSearch.ts +1 -1
  75. package/src/agents/tools/visionTool.ts +31 -2
  76. package/src/agents/tools/ycmd/client.ts +608 -0
  77. package/src/agents/tools/ycmd/definitions.ts +294 -0
  78. package/src/agents/tools/ycmd/detection.ts +211 -0
  79. package/src/agents/tools/ycmd/index.ts +11 -0
  80. package/src/agents/tools/ycmd/installer.ts +251 -0
  81. package/src/agents/tools/ycmd/server.ts +535 -0
  82. package/src/agents/tools/ycmd/serverManager.ts +316 -0
  83. package/src/agents/tools/ycmd/tools/completion.ts +113 -0
  84. package/src/agents/tools/ycmd/tools/diagnostics.ts +155 -0
  85. package/src/agents/tools/ycmd/tools/getLocations.ts +173 -0
  86. package/src/agents/tools/ycmd/tools/goto.ts +169 -0
  87. package/src/agents/tools/ycmd/tools/refactor.ts +204 -0
  88. package/src/agents/tools/ycmd/tools/signature.ts +174 -0
  89. package/src/agents/tools/ycmd/tools/start.ts +95 -0
  90. package/src/agents/tools/ycmd/utils/pathUtils.ts +59 -0
  91. package/src/ai.ts +15 -0
  92. package/src/chat/CliChatService.ts +277 -0
  93. package/src/chat/modules/AgentModule.ts +980 -0
  94. package/src/chat/modules/AskModule.ts +98 -0
  95. package/src/chat/modules/BaseChatModule.ts +66 -0
  96. package/src/chat/modules/InternalChatModule.ts +174 -0
  97. package/src/chat/modules/SearchModule.ts +166 -0
  98. package/src/chat/modules/SetupModule.ts +185 -0
  99. package/src/chat/modules/SystemModule.ts +120 -0
  100. package/src/chat/modules/VoiceModule.ts +70 -0
  101. package/src/chat/modules/index.js +5 -0
  102. package/src/chat/types.ts +97 -0
  103. package/src/chat.ts +9 -1
  104. package/src/chat2.ts +62 -0
  105. package/src/cli.ts +264 -35
  106. package/src/clients/anthropic.ts +14 -7
  107. package/src/clients/gemini.ts +15 -7
  108. package/src/clients/http.ts +17 -7
  109. package/src/clients/index.ts +117 -4
  110. package/src/clients/knowhow.ts +7 -2
  111. package/src/clients/knowhowMcp.ts +118 -0
  112. package/src/clients/openai.ts +32 -8
  113. package/src/clients/types.ts +1 -0
  114. package/src/clients/xai.ts +17 -5
  115. package/src/config.ts +30 -5
  116. package/src/conversion.ts +4 -1
  117. package/src/embeddings.ts +79 -23
  118. package/src/login.ts +26 -9
  119. package/src/microphone.ts +0 -1
  120. package/src/plugins/downloader/downloader.ts +72 -24
  121. package/src/plugins/downloader/plugin.ts +3 -1
  122. package/src/plugins/plugins.ts +3 -0
  123. package/src/processors/CustomVariables.ts +425 -0
  124. package/src/processors/HarmonyToolProcessor.ts +264 -0
  125. package/src/processors/XmlToolCallProcessor.ts +533 -0
  126. package/src/processors/index.ts +3 -0
  127. package/src/prompts/KnowhowConfigExamples.ts +376 -0
  128. package/src/services/KnowhowClient.ts +49 -3
  129. package/src/services/Mcp.ts +42 -3
  130. package/src/services/McpServer.ts +14 -4
  131. package/src/services/McpWebsocketTransport.ts +21 -7
  132. package/src/services/MessageProcessor.ts +10 -5
  133. package/src/services/index.ts +5 -0
  134. package/src/services/script-execution/ScriptExecutor.ts +34 -1
  135. package/src/services/types.ts +17 -14
  136. package/src/types.ts +17 -0
  137. package/src/utils/index.ts +138 -0
  138. package/tests/XmlToolCallProcessor.test.ts +468 -0
  139. package/tests/manual/ycmd/debug_diagnostics_test.ts +127 -0
  140. package/tests/manual/ycmd/fixtures/debug_diagnostics.ts +26 -0
  141. package/tests/manual/ycmd/fixtures/file_change_test.ts +17 -0
  142. package/tests/manual/ycmd/minimal_advanced_test.ts +108 -0
  143. package/tests/manual/ycmd/simple_diagnostics_test.ts +61 -0
  144. package/tests/manual/ycmd/simple_test.ts +74 -0
  145. package/tests/manual/ycmd/test-typescript-sample.ts +34 -0
  146. package/tests/manual/ycmd/test_advanced_features.ts +407 -0
  147. package/tests/manual/ycmd/test_advanced_with_tools.ts +320 -0
  148. package/tests/manual/ycmd/test_comprehensive_typescript.ts +179 -0
  149. package/tests/manual/ycmd/test_diagnostics_file_changes.ts +249 -0
  150. package/tests/manual/ycmd/test_diagnostics_fix.ts +99 -0
  151. package/tests/manual/ycmd/test_diagnostics_simple.ts +100 -0
  152. package/tests/manual/ycmd/test_diagnostics_timing.ts +120 -0
  153. package/tests/manual/ycmd/test_discover_commands.ts +310 -0
  154. package/tests/manual/ycmd/test_endpoints.ts +115 -0
  155. package/tests/manual/ycmd/test_final_comprehensive.ts +218 -0
  156. package/tests/manual/ycmd/test_final_validation.ts +150 -0
  157. package/tests/manual/ycmd/test_implementation.js +42 -0
  158. package/tests/manual/ycmd/test_individual_ycmd_tool.ts +39 -0
  159. package/tests/manual/ycmd/test_server_manager.ts +52 -0
  160. package/tests/manual/ycmd/test_simple_debug.ts +86 -0
  161. package/tests/manual/ycmd/test_tsserver_workflow.js +83 -0
  162. package/tests/manual/ycmd/test_tsserver_workflow.ts +122 -0
  163. package/tests/manual/ycmd/test_typescript_simple.ts +48 -0
  164. package/tests/manual/ycmd/test_typescript_ycmd.ts +105 -0
  165. package/tests/manual/ycmd/test_workspace_config.ts +90 -0
  166. package/tests/manual/ycmd/test_ycmd_auto_start.ts +137 -0
  167. package/tests/manual/ycmd/test_ycmd_comprehensive.ts +73 -0
  168. package/tests/manual/ycmd/test_ycmd_connection.py +10 -0
  169. package/tests/manual/ycmd/test_ycmd_direct.ts +142 -0
  170. package/tests/manual/ycmd/test_ycmd_experiment.ts +48 -0
  171. package/tests/manual/ycmd/test_ycmd_final.ts +200 -0
  172. package/tests/manual/ycmd/test_ycmd_fixed.py +18 -0
  173. package/tests/manual/ycmd/test_ycmd_integration.ts +112 -0
  174. package/tests/manual/ycmd/test_ycmd_simple.ts +45 -0
  175. package/tests/manual/ycmd/test_ycmd_usage.py +27 -0
  176. package/tests/manual/ycmd/working_simple_test.ts +134 -0
  177. package/ts_build/src/agents/base/base.d.ts +14 -1
  178. package/ts_build/src/agents/base/base.js +91 -17
  179. package/ts_build/src/agents/base/base.js.map +1 -1
  180. package/ts_build/src/agents/base/prompt.d.ts +1 -1
  181. package/ts_build/src/agents/base/prompt.js +28 -0
  182. package/ts_build/src/agents/base/prompt.js.map +1 -1
  183. package/ts_build/src/agents/index.d.ts +2 -0
  184. package/ts_build/src/agents/index.js +2 -0
  185. package/ts_build/src/agents/index.js.map +1 -1
  186. package/ts_build/src/agents/patcher/patcher.js +6 -3
  187. package/ts_build/src/agents/patcher/patcher.js.map +1 -1
  188. package/ts_build/src/agents/setup/setup.d.ts +8 -0
  189. package/ts_build/src/agents/setup/setup.js +59 -0
  190. package/ts_build/src/agents/setup/setup.js.map +1 -0
  191. package/ts_build/src/agents/tools/agentCall.js +5 -2
  192. package/ts_build/src/agents/tools/agentCall.js.map +1 -1
  193. package/ts_build/src/agents/tools/aiClient.d.ts +6 -5
  194. package/ts_build/src/agents/tools/aiClient.js +37 -6
  195. package/ts_build/src/agents/tools/aiClient.js.map +1 -1
  196. package/ts_build/src/agents/tools/execCommand.d.ts +2 -2
  197. package/ts_build/src/agents/tools/execCommand.js +5 -6
  198. package/ts_build/src/agents/tools/execCommand.js.map +1 -1
  199. package/ts_build/src/agents/tools/executeScript/index.d.ts +1 -1
  200. package/ts_build/src/agents/tools/index.d.ts +2 -0
  201. package/ts_build/src/agents/tools/index.js +2 -0
  202. package/ts_build/src/agents/tools/index.js.map +1 -1
  203. package/ts_build/src/agents/tools/list.js +66 -16
  204. package/ts_build/src/agents/tools/list.js.map +1 -1
  205. package/ts_build/src/agents/tools/startAgentTask.d.ts +13 -0
  206. package/ts_build/src/agents/tools/startAgentTask.js +74 -0
  207. package/ts_build/src/agents/tools/startAgentTask.js.map +1 -0
  208. package/ts_build/src/agents/tools/startChatTask.d.ts +13 -0
  209. package/ts_build/src/agents/tools/startChatTask.js +73 -0
  210. package/ts_build/src/agents/tools/startChatTask.js.map +1 -0
  211. package/ts_build/src/agents/tools/textSearch.js +1 -1
  212. package/ts_build/src/agents/tools/textSearch.js.map +1 -1
  213. package/ts_build/src/agents/tools/visionTool.d.ts +1 -1
  214. package/ts_build/src/agents/tools/visionTool.js +23 -3
  215. package/ts_build/src/agents/tools/visionTool.js.map +1 -1
  216. package/ts_build/src/agents/tools/ycmd/client.d.ts +93 -0
  217. package/ts_build/src/agents/tools/ycmd/client.js +355 -0
  218. package/ts_build/src/agents/tools/ycmd/client.js.map +1 -0
  219. package/ts_build/src/agents/tools/ycmd/definitions.d.ts +345 -0
  220. package/ts_build/src/agents/tools/ycmd/definitions.js +298 -0
  221. package/ts_build/src/agents/tools/ycmd/definitions.js.map +1 -0
  222. package/ts_build/src/agents/tools/ycmd/detection.d.ts +11 -0
  223. package/ts_build/src/agents/tools/ycmd/detection.js +175 -0
  224. package/ts_build/src/agents/tools/ycmd/detection.js.map +1 -0
  225. package/ts_build/src/agents/tools/ycmd/index.d.ts +8 -0
  226. package/ts_build/src/agents/tools/ycmd/index.js +20 -0
  227. package/ts_build/src/agents/tools/ycmd/index.js.map +1 -0
  228. package/ts_build/src/agents/tools/ycmd/installer.d.ts +19 -0
  229. package/ts_build/src/agents/tools/ycmd/installer.js +196 -0
  230. package/ts_build/src/agents/tools/ycmd/installer.js.map +1 -0
  231. package/ts_build/src/agents/tools/ycmd/server.d.ts +35 -0
  232. package/ts_build/src/agents/tools/ycmd/server.js +363 -0
  233. package/ts_build/src/agents/tools/ycmd/server.js.map +1 -0
  234. package/ts_build/src/agents/tools/ycmd/serverManager.d.ts +39 -0
  235. package/ts_build/src/agents/tools/ycmd/serverManager.js +210 -0
  236. package/ts_build/src/agents/tools/ycmd/serverManager.js.map +1 -0
  237. package/ts_build/src/agents/tools/ycmd/tools/completion.d.ts +22 -0
  238. package/ts_build/src/agents/tools/ycmd/tools/completion.js +72 -0
  239. package/ts_build/src/agents/tools/ycmd/tools/completion.js.map +1 -0
  240. package/ts_build/src/agents/tools/ycmd/tools/diagnostics.d.ts +42 -0
  241. package/ts_build/src/agents/tools/ycmd/tools/diagnostics.js +88 -0
  242. package/ts_build/src/agents/tools/ycmd/tools/diagnostics.js.map +1 -0
  243. package/ts_build/src/agents/tools/ycmd/tools/getLocations.d.ts +22 -0
  244. package/ts_build/src/agents/tools/ycmd/tools/getLocations.js +142 -0
  245. package/ts_build/src/agents/tools/ycmd/tools/getLocations.js.map +1 -0
  246. package/ts_build/src/agents/tools/ycmd/tools/goto.d.ts +20 -0
  247. package/ts_build/src/agents/tools/ycmd/tools/goto.js +101 -0
  248. package/ts_build/src/agents/tools/ycmd/tools/goto.js.map +1 -0
  249. package/ts_build/src/agents/tools/ycmd/tools/refactor.d.ts +32 -0
  250. package/ts_build/src/agents/tools/ycmd/tools/refactor.js +123 -0
  251. package/ts_build/src/agents/tools/ycmd/tools/refactor.js.map +1 -0
  252. package/ts_build/src/agents/tools/ycmd/tools/signature.d.ts +25 -0
  253. package/ts_build/src/agents/tools/ycmd/tools/signature.js +110 -0
  254. package/ts_build/src/agents/tools/ycmd/tools/signature.js.map +1 -0
  255. package/ts_build/src/agents/tools/ycmd/tools/start.d.ts +17 -0
  256. package/ts_build/src/agents/tools/ycmd/tools/start.js +65 -0
  257. package/ts_build/src/agents/tools/ycmd/tools/start.js.map +1 -0
  258. package/ts_build/src/agents/tools/ycmd/utils/pathUtils.d.ts +4 -0
  259. package/ts_build/src/agents/tools/ycmd/utils/pathUtils.js +67 -0
  260. package/ts_build/src/agents/tools/ycmd/utils/pathUtils.js.map +1 -0
  261. package/ts_build/src/ai.d.ts +1 -0
  262. package/ts_build/src/ai.js +40 -1
  263. package/ts_build/src/ai.js.map +1 -1
  264. package/ts_build/src/chat/ChatCommandHandler.d.ts +36 -0
  265. package/ts_build/src/chat/ChatCommandHandler.js +268 -0
  266. package/ts_build/src/chat/ChatCommandHandler.js.map +1 -0
  267. package/ts_build/src/chat/ChatInputManager.d.ts +22 -0
  268. package/ts_build/src/chat/ChatInputManager.js +85 -0
  269. package/ts_build/src/chat/ChatInputManager.js.map +1 -0
  270. package/ts_build/src/chat/ChatManager.d.ts +49 -0
  271. package/ts_build/src/chat/ChatManager.js +271 -0
  272. package/ts_build/src/chat/ChatManager.js.map +1 -0
  273. package/ts_build/src/chat/ChatSession.d.ts +32 -0
  274. package/ts_build/src/chat/ChatSession.js +3 -0
  275. package/ts_build/src/chat/ChatSession.js.map +1 -0
  276. package/ts_build/src/chat/ChatSessionManager.d.ts +19 -0
  277. package/ts_build/src/chat/ChatSessionManager.js +188 -0
  278. package/ts_build/src/chat/ChatSessionManager.js.map +1 -0
  279. package/ts_build/src/chat/ChatStateManager.d.ts +58 -0
  280. package/ts_build/src/chat/ChatStateManager.js +156 -0
  281. package/ts_build/src/chat/ChatStateManager.js.map +1 -0
  282. package/ts_build/src/chat/CliChatService.d.ts +35 -0
  283. package/ts_build/src/chat/CliChatService.js +201 -0
  284. package/ts_build/src/chat/CliChatService.js.map +1 -0
  285. package/ts_build/src/chat/InterruptibleInput.d.ts +20 -0
  286. package/ts_build/src/chat/InterruptibleInput.js +109 -0
  287. package/ts_build/src/chat/InterruptibleInput.js.map +1 -0
  288. package/ts_build/src/chat/interfaces/ChatModule.d.ts +6 -0
  289. package/ts_build/src/chat/interfaces/ChatModule.js +3 -0
  290. package/ts_build/src/chat/interfaces/ChatModule.js.map +1 -0
  291. package/ts_build/src/chat/modules/AgentModule.d.ts +56 -0
  292. package/ts_build/src/chat/modules/AgentModule.js +705 -0
  293. package/ts_build/src/chat/modules/AgentModule.js.map +1 -0
  294. package/ts_build/src/chat/modules/AskModule.d.ts +10 -0
  295. package/ts_build/src/chat/modules/AskModule.js +63 -0
  296. package/ts_build/src/chat/modules/AskModule.js.map +1 -0
  297. package/ts_build/src/chat/modules/BaseChatModule.d.ts +14 -0
  298. package/ts_build/src/chat/modules/BaseChatModule.js +32 -0
  299. package/ts_build/src/chat/modules/BaseChatModule.js.map +1 -0
  300. package/ts_build/src/chat/modules/InternalChatModule.d.ts +24 -0
  301. package/ts_build/src/chat/modules/InternalChatModule.js +127 -0
  302. package/ts_build/src/chat/modules/InternalChatModule.js.map +1 -0
  303. package/ts_build/src/chat/modules/SearchModule.d.ts +12 -0
  304. package/ts_build/src/chat/modules/SearchModule.js +119 -0
  305. package/ts_build/src/chat/modules/SearchModule.js.map +1 -0
  306. package/ts_build/src/chat/modules/SetupModule.d.ts +15 -0
  307. package/ts_build/src/chat/modules/SetupModule.js +147 -0
  308. package/ts_build/src/chat/modules/SetupModule.js.map +1 -0
  309. package/ts_build/src/chat/modules/SystemModule.d.ts +14 -0
  310. package/ts_build/src/chat/modules/SystemModule.js +90 -0
  311. package/ts_build/src/chat/modules/SystemModule.js.map +1 -0
  312. package/ts_build/src/chat/modules/VoiceModule.d.ts +11 -0
  313. package/ts_build/src/chat/modules/VoiceModule.js +57 -0
  314. package/ts_build/src/chat/modules/VoiceModule.js.map +1 -0
  315. package/ts_build/src/chat/types.d.ts +83 -0
  316. package/ts_build/src/chat/types.js +3 -0
  317. package/ts_build/src/chat/types.js.map +1 -0
  318. package/ts_build/src/chat.js +7 -1
  319. package/ts_build/src/chat.js.map +1 -1
  320. package/ts_build/src/chat2.d.ts +3 -0
  321. package/ts_build/src/chat2.js +47 -0
  322. package/ts_build/src/chat2.js.map +1 -0
  323. package/ts_build/src/cli.js +218 -37
  324. package/ts_build/src/cli.js.map +1 -1
  325. package/ts_build/src/clients/anthropic.d.ts +5 -2
  326. package/ts_build/src/clients/anthropic.js +12 -7
  327. package/ts_build/src/clients/anthropic.js.map +1 -1
  328. package/ts_build/src/clients/gemini.d.ts +6 -3
  329. package/ts_build/src/clients/gemini.js +13 -7
  330. package/ts_build/src/clients/gemini.js.map +1 -1
  331. package/ts_build/src/clients/http.d.ts +1 -0
  332. package/ts_build/src/clients/http.js +12 -5
  333. package/ts_build/src/clients/http.js.map +1 -1
  334. package/ts_build/src/clients/index.d.ts +10 -0
  335. package/ts_build/src/clients/index.js +74 -4
  336. package/ts_build/src/clients/index.js.map +1 -1
  337. package/ts_build/src/clients/knowhow.d.ts +3 -1
  338. package/ts_build/src/clients/knowhow.js +8 -2
  339. package/ts_build/src/clients/knowhow.js.map +1 -1
  340. package/ts_build/src/clients/knowhowMcp.d.ts +20 -0
  341. package/ts_build/src/clients/knowhowMcp.js +86 -0
  342. package/ts_build/src/clients/knowhowMcp.js.map +1 -0
  343. package/ts_build/src/clients/openai.d.ts +5 -2
  344. package/ts_build/src/clients/openai.js +29 -8
  345. package/ts_build/src/clients/openai.js.map +1 -1
  346. package/ts_build/src/clients/types.d.ts +1 -0
  347. package/ts_build/src/clients/xai.d.ts +5 -2
  348. package/ts_build/src/clients/xai.js +15 -5
  349. package/ts_build/src/clients/xai.js.map +1 -1
  350. package/ts_build/src/config.js +24 -3
  351. package/ts_build/src/config.js.map +1 -1
  352. package/ts_build/src/conversion.js +6 -4
  353. package/ts_build/src/conversion.js.map +1 -1
  354. package/ts_build/src/embeddings.d.ts +2 -1
  355. package/ts_build/src/embeddings.js +62 -17
  356. package/ts_build/src/embeddings.js.map +1 -1
  357. package/ts_build/src/login.d.ts +1 -1
  358. package/ts_build/src/login.js +21 -7
  359. package/ts_build/src/login.js.map +1 -1
  360. package/ts_build/src/microphone.js.map +1 -1
  361. package/ts_build/src/plugins/downloader/downloader.d.ts +4 -5
  362. package/ts_build/src/plugins/downloader/downloader.js +55 -26
  363. package/ts_build/src/plugins/downloader/downloader.js.map +1 -1
  364. package/ts_build/src/plugins/downloader/plugin.js +5 -3
  365. package/ts_build/src/plugins/downloader/plugin.js.map +1 -1
  366. package/ts_build/src/plugins/plugins.js +3 -0
  367. package/ts_build/src/plugins/plugins.js.map +1 -1
  368. package/ts_build/src/processors/CustomVariables.d.ts +32 -0
  369. package/ts_build/src/processors/CustomVariables.js +297 -0
  370. package/ts_build/src/processors/CustomVariables.js.map +1 -0
  371. package/ts_build/src/processors/HarmonyToolProcessor.d.ts +15 -0
  372. package/ts_build/src/processors/HarmonyToolProcessor.js +154 -0
  373. package/ts_build/src/processors/HarmonyToolProcessor.js.map +1 -0
  374. package/ts_build/src/processors/XmlToolCallProcessor.d.ts +14 -0
  375. package/ts_build/src/processors/XmlToolCallProcessor.js +357 -0
  376. package/ts_build/src/processors/XmlToolCallProcessor.js.map +1 -0
  377. package/ts_build/src/processors/index.d.ts +3 -0
  378. package/ts_build/src/processors/index.js +7 -1
  379. package/ts_build/src/processors/index.js.map +1 -1
  380. package/ts_build/src/prompts/KnowhowConfigExamples.d.ts +2 -0
  381. package/ts_build/src/prompts/KnowhowConfigExamples.js +379 -0
  382. package/ts_build/src/prompts/KnowhowConfigExamples.js.map +1 -0
  383. package/ts_build/src/services/KnowhowClient.d.ts +22 -0
  384. package/ts_build/src/services/KnowhowClient.js +14 -2
  385. package/ts_build/src/services/KnowhowClient.js.map +1 -1
  386. package/ts_build/src/services/Mcp.d.ts +1 -0
  387. package/ts_build/src/services/Mcp.js +20 -3
  388. package/ts_build/src/services/Mcp.js.map +1 -1
  389. package/ts_build/src/services/McpServer.d.ts +1 -1
  390. package/ts_build/src/services/McpServer.js +8 -4
  391. package/ts_build/src/services/McpServer.js.map +1 -1
  392. package/ts_build/src/services/McpWebsocketTransport.js +17 -7
  393. package/ts_build/src/services/McpWebsocketTransport.js.map +1 -1
  394. package/ts_build/src/services/MessageProcessor.d.ts +1 -1
  395. package/ts_build/src/services/MessageProcessor.js +4 -4
  396. package/ts_build/src/services/MessageProcessor.js.map +1 -1
  397. package/ts_build/src/services/index.d.ts +2 -0
  398. package/ts_build/src/services/index.js +4 -0
  399. package/ts_build/src/services/index.js.map +1 -1
  400. package/ts_build/src/services/script-execution/ScriptExecutor.d.ts +1 -0
  401. package/ts_build/src/services/script-execution/ScriptExecutor.js +23 -0
  402. package/ts_build/src/services/script-execution/ScriptExecutor.js.map +1 -1
  403. package/ts_build/src/services/types.d.ts +2 -6
  404. package/ts_build/src/services/types.js +4 -4
  405. package/ts_build/src/services/types.js.map +1 -1
  406. package/ts_build/src/types.d.ts +11 -0
  407. package/ts_build/src/types.js +8 -0
  408. package/ts_build/src/types.js.map +1 -1
  409. package/ts_build/src/utils/index.d.ts +2 -0
  410. package/ts_build/src/utils/index.js +102 -1
  411. package/ts_build/src/utils/index.js.map +1 -1
  412. package/ts_build/tests/XmlToolCallProcessor.test.d.ts +1 -0
  413. package/ts_build/tests/XmlToolCallProcessor.test.js +376 -0
  414. package/ts_build/tests/XmlToolCallProcessor.test.js.map +1 -0
  415. package/ts_build/tests/manual/ycmd/debug_diagnostics_test.d.ts +1 -0
  416. package/ts_build/tests/manual/ycmd/debug_diagnostics_test.js +114 -0
  417. package/ts_build/tests/manual/ycmd/debug_diagnostics_test.js.map +1 -0
  418. package/ts_build/tests/manual/ycmd/minimal_advanced_test.d.ts +2 -0
  419. package/ts_build/tests/manual/ycmd/minimal_advanced_test.js +104 -0
  420. package/ts_build/tests/manual/ycmd/minimal_advanced_test.js.map +1 -0
  421. package/ts_build/tests/manual/ycmd/simple_diagnostics_test.d.ts +1 -0
  422. package/ts_build/tests/manual/ycmd/simple_diagnostics_test.js +74 -0
  423. package/ts_build/tests/manual/ycmd/simple_diagnostics_test.js.map +1 -0
  424. package/ts_build/tests/manual/ycmd/simple_test.d.ts +2 -0
  425. package/ts_build/tests/manual/ycmd/simple_test.js +82 -0
  426. package/ts_build/tests/manual/ycmd/simple_test.js.map +1 -0
  427. package/ts_build/tests/manual/ycmd/test-typescript-sample.d.ts +14 -0
  428. package/ts_build/tests/manual/ycmd/test-typescript-sample.js +20 -0
  429. package/ts_build/tests/manual/ycmd/test-typescript-sample.js.map +1 -0
  430. package/ts_build/tests/manual/ycmd/test_advanced_features.d.ts +2 -0
  431. package/ts_build/tests/manual/ycmd/test_advanced_features.js +297 -0
  432. package/ts_build/tests/manual/ycmd/test_advanced_features.js.map +1 -0
  433. package/ts_build/tests/manual/ycmd/test_advanced_with_tools.d.ts +3 -0
  434. package/ts_build/tests/manual/ycmd/test_advanced_with_tools.js +262 -0
  435. package/ts_build/tests/manual/ycmd/test_advanced_with_tools.js.map +1 -0
  436. package/ts_build/tests/manual/ycmd/test_comprehensive_typescript.d.ts +2 -0
  437. package/ts_build/tests/manual/ycmd/test_comprehensive_typescript.js +186 -0
  438. package/ts_build/tests/manual/ycmd/test_comprehensive_typescript.js.map +1 -0
  439. package/ts_build/tests/manual/ycmd/test_diagnostics_file_changes.d.ts +1 -0
  440. package/ts_build/tests/manual/ycmd/test_diagnostics_file_changes.js +174 -0
  441. package/ts_build/tests/manual/ycmd/test_diagnostics_file_changes.js.map +1 -0
  442. package/ts_build/tests/manual/ycmd/test_diagnostics_fix.d.ts +2 -0
  443. package/ts_build/tests/manual/ycmd/test_diagnostics_fix.js +106 -0
  444. package/ts_build/tests/manual/ycmd/test_diagnostics_fix.js.map +1 -0
  445. package/ts_build/tests/manual/ycmd/test_diagnostics_simple.d.ts +1 -0
  446. package/ts_build/tests/manual/ycmd/test_diagnostics_simple.js +104 -0
  447. package/ts_build/tests/manual/ycmd/test_diagnostics_simple.js.map +1 -0
  448. package/ts_build/tests/manual/ycmd/test_diagnostics_timing.d.ts +1 -0
  449. package/ts_build/tests/manual/ycmd/test_diagnostics_timing.js +119 -0
  450. package/ts_build/tests/manual/ycmd/test_diagnostics_timing.js.map +1 -0
  451. package/ts_build/tests/manual/ycmd/test_discover_commands.d.ts +2 -0
  452. package/ts_build/tests/manual/ycmd/test_discover_commands.js +243 -0
  453. package/ts_build/tests/manual/ycmd/test_discover_commands.js.map +1 -0
  454. package/ts_build/tests/manual/ycmd/test_endpoints.d.ts +2 -0
  455. package/ts_build/tests/manual/ycmd/test_endpoints.js +120 -0
  456. package/ts_build/tests/manual/ycmd/test_endpoints.js.map +1 -0
  457. package/ts_build/tests/manual/ycmd/test_final_comprehensive.d.ts +2 -0
  458. package/ts_build/tests/manual/ycmd/test_final_comprehensive.js +221 -0
  459. package/ts_build/tests/manual/ycmd/test_final_comprehensive.js.map +1 -0
  460. package/ts_build/tests/manual/ycmd/test_final_validation.d.ts +2 -0
  461. package/ts_build/tests/manual/ycmd/test_final_validation.js +160 -0
  462. package/ts_build/tests/manual/ycmd/test_final_validation.js.map +1 -0
  463. package/ts_build/tests/manual/ycmd/test_individual_ycmd_tool.d.ts +2 -0
  464. package/ts_build/tests/manual/ycmd/test_individual_ycmd_tool.js +37 -0
  465. package/ts_build/tests/manual/ycmd/test_individual_ycmd_tool.js.map +1 -0
  466. package/ts_build/tests/manual/ycmd/test_server_manager.d.ts +1 -0
  467. package/ts_build/tests/manual/ycmd/test_server_manager.js +38 -0
  468. package/ts_build/tests/manual/ycmd/test_server_manager.js.map +1 -0
  469. package/ts_build/tests/manual/ycmd/test_simple_debug.d.ts +2 -0
  470. package/ts_build/tests/manual/ycmd/test_simple_debug.js +99 -0
  471. package/ts_build/tests/manual/ycmd/test_simple_debug.js.map +1 -0
  472. package/ts_build/tests/manual/ycmd/test_tsserver_workflow.d.ts +1 -0
  473. package/ts_build/tests/manual/ycmd/test_tsserver_workflow.js +128 -0
  474. package/ts_build/tests/manual/ycmd/test_tsserver_workflow.js.map +1 -0
  475. package/ts_build/tests/manual/ycmd/test_typescript_simple.d.ts +1 -0
  476. package/ts_build/tests/manual/ycmd/test_typescript_simple.js +66 -0
  477. package/ts_build/tests/manual/ycmd/test_typescript_simple.js.map +1 -0
  478. package/ts_build/tests/manual/ycmd/test_typescript_ycmd.d.ts +1 -0
  479. package/ts_build/tests/manual/ycmd/test_typescript_ycmd.js +105 -0
  480. package/ts_build/tests/manual/ycmd/test_typescript_ycmd.js.map +1 -0
  481. package/ts_build/tests/manual/ycmd/test_workspace_config.d.ts +1 -0
  482. package/ts_build/tests/manual/ycmd/test_workspace_config.js +89 -0
  483. package/ts_build/tests/manual/ycmd/test_workspace_config.js.map +1 -0
  484. package/ts_build/tests/manual/ycmd/test_ycmd_auto_start.d.ts +2 -0
  485. package/ts_build/tests/manual/ycmd/test_ycmd_auto_start.js +130 -0
  486. package/ts_build/tests/manual/ycmd/test_ycmd_auto_start.js.map +1 -0
  487. package/ts_build/tests/manual/ycmd/test_ycmd_comprehensive.d.ts +1 -0
  488. package/ts_build/tests/manual/ycmd/test_ycmd_comprehensive.js +83 -0
  489. package/ts_build/tests/manual/ycmd/test_ycmd_comprehensive.js.map +1 -0
  490. package/ts_build/tests/manual/ycmd/test_ycmd_direct.d.ts +2 -0
  491. package/ts_build/tests/manual/ycmd/test_ycmd_direct.js +149 -0
  492. package/ts_build/tests/manual/ycmd/test_ycmd_direct.js.map +1 -0
  493. package/ts_build/tests/manual/ycmd/test_ycmd_experiment.d.ts +15 -0
  494. package/ts_build/tests/manual/ycmd/test_ycmd_experiment.js +58 -0
  495. package/ts_build/tests/manual/ycmd/test_ycmd_experiment.js.map +1 -0
  496. package/ts_build/tests/manual/ycmd/test_ycmd_final.d.ts +2 -0
  497. package/ts_build/tests/manual/ycmd/test_ycmd_final.js +195 -0
  498. package/ts_build/tests/manual/ycmd/test_ycmd_final.js.map +1 -0
  499. package/ts_build/tests/manual/ycmd/test_ycmd_integration.d.ts +3 -0
  500. package/ts_build/tests/manual/ycmd/test_ycmd_integration.js +110 -0
  501. package/ts_build/tests/manual/ycmd/test_ycmd_integration.js.map +1 -0
  502. package/ts_build/tests/manual/ycmd/test_ycmd_simple.d.ts +2 -0
  503. package/ts_build/tests/manual/ycmd/test_ycmd_simple.js +36 -0
  504. package/ts_build/tests/manual/ycmd/test_ycmd_simple.js.map +1 -0
  505. package/ts_build/tests/manual/ycmd/working_simple_test.d.ts +2 -0
  506. package/ts_build/tests/manual/ycmd/working_simple_test.js +134 -0
  507. package/ts_build/tests/manual/ycmd/working_simple_test.js.map +1 -0
  508. package/tsconfig.json +3 -1
@@ -0,0 +1,533 @@
1
+ import { Message, ToolCall } from "../clients/types";
2
+ import { MessageProcessorFunction } from "../services/MessageProcessor";
3
+
4
+ export class XmlToolCallProcessor {
5
+ private static instance: XmlToolCallProcessor;
6
+
7
+ /**
8
+ * Get singleton instance
9
+ */
10
+ static getInstance(): XmlToolCallProcessor {
11
+ if (!XmlToolCallProcessor.instance) {
12
+ XmlToolCallProcessor.instance = new XmlToolCallProcessor();
13
+ }
14
+ return XmlToolCallProcessor.instance;
15
+ }
16
+
17
+ /**
18
+ * Detects XML tool call patterns in text content
19
+ * Supports various XML formats that might appear in assistant outputs
20
+ */
21
+ private detectXmlToolCalls(content: string): RegExpMatchArray[] {
22
+ // Pattern to match XML tool calls with various formats:
23
+ // Look for tool_call tags specifically
24
+ const toolCallMatches = content.match(/<tool_call>/g);
25
+ // <tool_call name="toolName">arguments</tool_call>
26
+ // <tool_call name="toolName" arguments="json_args"/>
27
+ // <toolCall name="toolName">arguments</toolCall>
28
+ // <function_call name="toolName">arguments</function_call>
29
+ // Pattern for self-closing attribute-based tool calls:
30
+ // <tool_call name="toolName" arguments="json_args"/>
31
+ const xmlToolCallPattern1SelfClosing =
32
+ /<(?:tool_call|toolCall|function_call)\s+name=["']([^"']+)["']\s+arguments=(['"])((?:\\.|(?!\2)[^\\])*?)\2[^>]*\/>/g;
33
+
34
+
35
+ // <tool_call>{"name": "toolName", "arguments": {...}}</tool_call>
36
+ const xmlToolCallPattern1 =
37
+ /<(?:tool_call|toolCall|function_call)\s+name=["']([^"']+)["'](?:\s+arguments=["']([^"']*)["'])?[^>]*>([^<]*)<\/(?:tool_call|toolCall|function_call)>/g;
38
+
39
+ // Pattern for JSON-based tool calls:
40
+ // <tool_call>{"name": "toolName", "arguments": {...}}</tool_call>
41
+ // Updated to handle complex nested JSON with braces and multiline content
42
+ const xmlToolCallPattern2 =
43
+ /<(?:tool_call|toolCall|function_call)>\s*(\{(?:[^{}]|{[^{}]*})*?"name"\s*:\s*"([^"]+)"(?:[^{}]|{[^{}]*})*?\})\s*<\/(?:tool_call|toolCall|function_call)>/gs;
44
+
45
+ // Fallback pattern for very complex nested JSON
46
+ const xmlToolCallPattern2Complex = /<(?:tool_call|toolCall|function_call)>\s*(\{[\s\S]*?\})\s*<\/(?:tool_call|toolCall|function_call)>/g;
47
+
48
+ // Pattern for nested XML tool calls:
49
+ // <tool_call><invoke name="toolName"><parameter name="paramName">value</parameter></invoke></tool_call>
50
+ const xmlToolCallPattern3 =
51
+ /<(?:tool_call|toolCall|function_call)>\s*<invoke\s+name=["']([^"']+)["']>\s*(.*?)\s*<\/invoke>\s*<\/(?:tool_call|toolCall|function_call)>/gs;
52
+ const processedRanges: Array<{start: number, end: number}> = [];
53
+
54
+ const matches: RegExpMatchArray[] = [];
55
+ let match;
56
+
57
+ // Reset regex lastIndex for self-closing pattern
58
+ xmlToolCallPattern1SelfClosing.lastIndex = 0;
59
+
60
+ // Self-closing attribute-based pattern
61
+ while ((match = xmlToolCallPattern1SelfClosing.exec(content)) !== null) {
62
+ // For self-closing tags, there's no inner content, so set it to empty string
63
+ const [fullMatch, toolName, quoteChar, argsAttribute] = match;
64
+ const selfClosingMatch = [fullMatch, toolName, argsAttribute, ""] as RegExpMatchArray;
65
+ selfClosingMatch.index = match.index;
66
+ selfClosingMatch.input = match.input;
67
+ matches.push(selfClosingMatch);
68
+ processedRanges.push({start: match.index!, end: match.index! + match[0].length});
69
+ }
70
+
71
+ // First pattern: attribute-based
72
+ while ((match = xmlToolCallPattern1.exec(content)) !== null) {
73
+ matches.push(match);
74
+ }
75
+
76
+ // Reset regex lastIndex for second pattern
77
+ xmlToolCallPattern1.lastIndex = 0;
78
+
79
+ xmlToolCallPattern2.lastIndex = 0;
80
+
81
+ // Second pattern: JSON-based
82
+ while ((match = xmlToolCallPattern2.exec(content)) !== null) {
83
+ // For JSON-based matches, we need to extract just the arguments part
84
+ // Check if this range is already processed
85
+ const matchStart = match.index!;
86
+ const matchEnd = matchStart + match[0].length;
87
+ const alreadyProcessed = processedRanges.some(range =>
88
+ (matchStart >= range.start && matchStart < range.end) ||
89
+ (matchEnd > range.start && matchEnd <= range.end)
90
+ );
91
+ if (alreadyProcessed) continue;
92
+
93
+ const [fullMatch, jsonContent, toolName] = match;
94
+
95
+ try {
96
+
97
+ // Handle the case where arguments might be an unescaped JSON string
98
+ // First, try to fix common JSON parsing issues
99
+ let fixedJsonContent = jsonContent;
100
+
101
+ // Look for the pattern: "arguments": "{...}" where the inner JSON has unescaped quotes
102
+ const argumentsStringMatch = jsonContent.match(/"arguments"\s*:\s*"(\{.*\})"/);
103
+ if (argumentsStringMatch) {
104
+ // Extract the inner JSON string and properly escape it
105
+ const innerJson = argumentsStringMatch[1];
106
+ const escapedInnerJson = innerJson.replace(/"/g, '\\"');
107
+ fixedJsonContent = jsonContent.replace(
108
+ /"arguments"\s*:\s*"\{.*\}"/,
109
+ `"arguments": "${escapedInnerJson}"`
110
+ );
111
+ }
112
+
113
+ const parsed = JSON.parse(fixedJsonContent);
114
+ let argumentsContent = parsed.arguments || "{}";
115
+
116
+ // If arguments is a string, it might be a JSON string that needs parsing
117
+ if (typeof argumentsContent === 'string') {
118
+ // Try to parse the string as JSON to validate it
119
+ try {
120
+ const parsedArgs = JSON.parse(argumentsContent);
121
+ // If it parses successfully, use the original string
122
+ argumentsContent = argumentsContent;
123
+ } catch {
124
+ // If it doesn't parse, it might need to be wrapped as a string value
125
+ argumentsContent = JSON.stringify({ input: argumentsContent });
126
+ }
127
+ } else {
128
+ argumentsContent = JSON.stringify(argumentsContent);
129
+ }
130
+
131
+ // Restructure match to fit expected format [fullMatch, toolName, argsAttribute, innerContent]
132
+ const restructuredMatch = [
133
+ fullMatch,
134
+ toolName,
135
+ undefined,
136
+ argumentsContent,
137
+ ] as RegExpMatchArray;
138
+ restructuredMatch.index = match.index;
139
+ restructuredMatch.input = match.input;
140
+ matches.push(restructuredMatch);
141
+ processedRanges.push({start: matchStart, end: matchEnd});
142
+ } catch (error) {
143
+ // Try string-based parsing as fallback when JSON.parse fails
144
+ try {
145
+ const stringBlocks = this.extractToolCallBlocks(fullMatch);
146
+ if (stringBlocks.length > 0) {
147
+ const block = stringBlocks[0]; // Take the first block found
148
+ const restructuredMatch = [fullMatch, block.name, block.arguments, ""] as RegExpMatchArray;
149
+ restructuredMatch.index = match.index;
150
+ restructuredMatch.input = match.input;
151
+ matches.push(restructuredMatch);
152
+ processedRanges.push({start: matchStart, end: matchEnd});
153
+ } else {
154
+ // If string-based parsing also fails, skip this match
155
+ continue;
156
+ }
157
+ } catch (stringError) {
158
+ // If both JSON and string parsing fail, skip this match
159
+ continue;
160
+ }
161
+ }
162
+ }
163
+
164
+ // Reset regex lastIndex for complex pattern
165
+ xmlToolCallPattern2Complex.lastIndex = 0;
166
+
167
+ // Fallback: Try complex pattern for deeply nested JSON
168
+ while ((match = xmlToolCallPattern2Complex.exec(content)) !== null) {
169
+ // Check if this range is already processed
170
+ const matchStart = match.index!;
171
+ const matchEnd = matchStart + match[0].length;
172
+ const alreadyProcessed = processedRanges.some(range =>
173
+ (matchStart >= range.start && matchStart < range.end) ||
174
+ (matchEnd > range.start && matchEnd <= range.end)
175
+ );
176
+ if (alreadyProcessed) continue;
177
+
178
+ const [fullMatch, jsonContent, ...rest] = match;
179
+
180
+ try {
181
+ const parsed = JSON.parse(jsonContent);
182
+ const toolName = parsed.name;
183
+
184
+ if (toolName) {
185
+ let argumentsContent = parsed.arguments || "{}";
186
+
187
+ // Convert arguments to string if it's an object
188
+ if (typeof argumentsContent === 'object') {
189
+ argumentsContent = JSON.stringify(argumentsContent);
190
+ }
191
+
192
+ const restructuredMatch = [fullMatch, toolName, argumentsContent, ""] as RegExpMatchArray;
193
+ restructuredMatch.index = match.index;
194
+ restructuredMatch.input = match.input;
195
+ matches.push(restructuredMatch);
196
+ processedRanges.push({start: matchStart, end: matchEnd});
197
+ }
198
+ } catch (error) {
199
+ // Skip this match if JSON parsing fails
200
+ continue;
201
+ }
202
+ }
203
+
204
+ // Reset regex lastIndex for third pattern
205
+ xmlToolCallPattern3.lastIndex = 0;
206
+
207
+ // Third pattern: nested XML-based
208
+ while ((match = xmlToolCallPattern3.exec(content)) !== null) {
209
+ // Restructure match to fit expected format [fullMatch, toolName, argsAttribute, innerContent]
210
+ const [fullMatch, toolName, innerXml] = match;
211
+ const restructuredMatch = [
212
+ fullMatch,
213
+ toolName,
214
+ undefined,
215
+ innerXml,
216
+ ] as RegExpMatchArray;
217
+ restructuredMatch.index = match.index;
218
+ restructuredMatch.input = match.input;
219
+ matches.push(restructuredMatch);
220
+ }
221
+
222
+ return matches;
223
+ }
224
+
225
+ /**
226
+ * Parses XML tool call arguments from various formats
227
+ */
228
+ private parseToolCallArguments(
229
+ argsAttribute: string | undefined,
230
+ innerContent: string | any
231
+ ): string {
232
+ // Handle non-string innerContent (can happen with restructured matches)
233
+ if (innerContent && typeof innerContent !== 'string') {
234
+ return typeof innerContent === 'object' ? JSON.stringify(innerContent) : String(innerContent);
235
+ }
236
+
237
+ // For JSON-based XML calls, innerContent is now already the arguments part
238
+ if (innerContent && typeof innerContent === 'string' && innerContent.trim()) {
239
+ const trimmedContent = innerContent.trim();
240
+
241
+ // If it's already valid JSON, return it
242
+ try {
243
+ JSON.parse(trimmedContent);
244
+ return trimmedContent;
245
+ } catch {
246
+ // If it's not valid JSON, we'll handle it below
247
+ }
248
+ }
249
+
250
+ // Check if innerContent contains nested XML parameters (like <parameter name="key">value</parameter>)
251
+ if (innerContent && innerContent.includes("<parameter")) {
252
+ try {
253
+ const parameterPattern =
254
+ /<parameter\s+name=["']([^"']+)["']>([^<]*)<\/parameter>/g;
255
+ const parameters: any = {};
256
+ let paramMatch;
257
+
258
+ while ((paramMatch = parameterPattern.exec(innerContent)) !== null) {
259
+ const [, paramName, paramValue] = paramMatch;
260
+ parameters[paramName] = paramValue.trim();
261
+ }
262
+
263
+ if (Object.keys(parameters).length > 0) {
264
+ return JSON.stringify(parameters);
265
+ }
266
+ } catch (error) {
267
+ // Fall through to existing logic
268
+ }
269
+ }
270
+
271
+ // If arguments are in attribute, use that
272
+ if (argsAttribute && argsAttribute.trim()) {
273
+ return argsAttribute.trim();
274
+ }
275
+
276
+ // Otherwise, try to parse inner content
277
+ if (innerContent && innerContent.trim()) {
278
+ const trimmedContent = innerContent.trim();
279
+
280
+ // Check if it's already JSON
281
+ try {
282
+ JSON.parse(trimmedContent);
283
+ return trimmedContent;
284
+ } catch {
285
+ // If not JSON, try to extract key-value pairs or treat as single argument
286
+ if (trimmedContent.includes("=") || trimmedContent.includes(":")) {
287
+ // Try to convert key=value pairs to JSON
288
+ try {
289
+ const jsonArgs: any = {};
290
+ const pairs = trimmedContent.split(/[,\n]/);
291
+
292
+ for (const pair of pairs) {
293
+ const trimmedPair = pair.trim();
294
+ if (trimmedPair.includes("=")) {
295
+ const [key, ...valueParts] = trimmedPair.split("=");
296
+ const value = valueParts.join("=").trim();
297
+ jsonArgs[key.trim()] = value.replace(/^["']|["']$/g, ""); // Remove quotes
298
+ } else if (trimmedPair.includes(":")) {
299
+ const [key, ...valueParts] = trimmedPair.split(":");
300
+ const value = valueParts.join(":").trim();
301
+ jsonArgs[key.trim()] = value.replace(/^["']|["']$/g, ""); // Remove quotes
302
+ }
303
+ }
304
+
305
+ if (Object.keys(jsonArgs).length > 0) {
306
+ return JSON.stringify(jsonArgs);
307
+ }
308
+ } catch {
309
+ // Fall through to default handling
310
+ }
311
+ }
312
+
313
+ // If all else fails, wrap in a generic argument structure
314
+ return JSON.stringify({ input: trimmedContent });
315
+ }
316
+ }
317
+
318
+ // Default empty arguments
319
+ return "{}";
320
+ }
321
+
322
+ /**
323
+ * Generates a unique tool call ID
324
+ */
325
+ private generateToolCallId(): string {
326
+ return `call_${Date.now()}_${Math.random().toString(36).substr(2, 9)}`;
327
+ }
328
+
329
+ /**
330
+ * Converts XML tool call matches to proper ToolCall objects
331
+ */
332
+ private convertXmlToToolCalls(matches: RegExpMatchArray[]): ToolCall[] {
333
+ const toolCalls: ToolCall[] = [];
334
+
335
+ for (const match of matches) {
336
+ const [fullMatch, toolName, argsAttribute, innerContent] = match;
337
+
338
+ if (!toolName) continue;
339
+
340
+ const toolCall: ToolCall = {
341
+ id: this.generateToolCallId(),
342
+ type: "function",
343
+ function: {
344
+ name: toolName,
345
+ arguments: this.parseToolCallArguments(argsAttribute, innerContent),
346
+ },
347
+ };
348
+
349
+ toolCalls.push(toolCall);
350
+ }
351
+
352
+ return toolCalls;
353
+ }
354
+
355
+ /**
356
+ * Detects incomplete XML tool calls that are missing closing tags
357
+ * This handles cases where the AI finishes the JSON but not the closing tag
358
+ */
359
+ private detectIncompleteToolCalls(content: string): { name: string; arguments: string }[] {
360
+ const blocks: { name: string; arguments: string }[] = [];
361
+ let startIndex = 0;
362
+
363
+ while (true) {
364
+ const toolCallStart = content.indexOf('<tool_call>', startIndex);
365
+ if (toolCallStart === -1) break;
366
+
367
+ const toolCallEnd = content.indexOf('</tool_call>', toolCallStart);
368
+
369
+ // If no closing tag found, check if we have complete JSON at the end
370
+ if (toolCallEnd === -1) {
371
+ const jsonStart = toolCallStart + '<tool_call>'.length;
372
+ const remainingContent = content.substring(jsonStart).trim();
373
+
374
+ // Try to parse the remaining content as JSON
375
+ try {
376
+ const parsed = JSON.parse(remainingContent);
377
+ if (parsed.name && parsed.arguments !== undefined) {
378
+ blocks.push({
379
+ name: parsed.name,
380
+ arguments: typeof parsed.arguments === 'string' ? parsed.arguments : JSON.stringify(parsed.arguments),
381
+ });
382
+ }
383
+ } catch (error) {
384
+ // If JSON parsing fails, this might be incomplete or malformed
385
+ // We'll skip it for now
386
+ }
387
+
388
+ // Move past this opening tag for next iteration
389
+ startIndex = toolCallStart + '<tool_call>'.length;
390
+ continue;
391
+ }
392
+
393
+ // If we found a closing tag, move past it for next iteration
394
+ startIndex = toolCallEnd + '</tool_call>'.length;
395
+ }
396
+
397
+ return blocks;
398
+ }
399
+
400
+ /**
401
+ * Simple string-based extractor for tool call blocks
402
+ */
403
+ private extractToolCallBlocks(content: string): { name: string; arguments: string }[] {
404
+ const blocks: { name: string; arguments: string }[] = [];
405
+ let startIndex = 0;
406
+
407
+ while (true) {
408
+ const toolCallStart = content.indexOf('<tool_call>', startIndex);
409
+ if (toolCallStart === -1) break;
410
+
411
+ const toolCallEnd = content.indexOf('</tool_call>', toolCallStart);
412
+ if (toolCallEnd === -1) break;
413
+
414
+ // Extract JSON content between tags
415
+ const jsonStart = toolCallStart + '<tool_call>'.length;
416
+ const jsonContent = content.substring(jsonStart, toolCallEnd).trim();
417
+
418
+ try {
419
+ // Try to parse the JSON content directly first
420
+ const parsed = JSON.parse(jsonContent);
421
+ if (parsed.name && parsed.arguments !== undefined) {
422
+ blocks.push({
423
+ name: parsed.name,
424
+ arguments: typeof parsed.arguments === 'string' ? parsed.arguments : JSON.stringify(parsed.arguments),
425
+ });
426
+ }
427
+ } catch (error: any) {
428
+
429
+ // Try to fix common JSON issues like unescaped newlines
430
+ try {
431
+ // More robust approach: escape all control characters in JSON string values
432
+ let fixedContent = jsonContent;
433
+
434
+ // Find all JSON string values and escape control characters within them
435
+ fixedContent = fixedContent.replace(/"((?:[^"\\]|\\.)*)"/g, (match, content) => {
436
+ const escapedContent = content
437
+ .replace(/\\/g, '\\\\') // Escape backslashes first
438
+ .replace(/\n/g, '\\n') // Escape newlines
439
+ .replace(/\r/g, '\\r') // Escape carriage returns
440
+ .replace(/\t/g, '\\t'); // Escape tabs
441
+ return `"${escapedContent}"`;
442
+ });
443
+
444
+ const parsed = JSON.parse(fixedContent);
445
+ if (parsed.name && parsed.arguments !== undefined) {
446
+ blocks.push({
447
+ name: parsed.name,
448
+ arguments: typeof parsed.arguments === 'string' ? parsed.arguments : JSON.stringify(parsed.arguments),
449
+ });
450
+ }
451
+ } catch (secondError) {
452
+ // Silent failure - couldn't parse this tool call
453
+ }
454
+ }
455
+
456
+ startIndex = toolCallEnd + '</tool_call>'.length;
457
+ }
458
+
459
+ return blocks;
460
+ }
461
+
462
+ /**
463
+ * Processes a single message to detect and transform XML tool calls
464
+ */
465
+ private processMessage(message: Message): void {
466
+ // Only process assistant messages that might contain XML tool calls
467
+ if (message.role !== "assistant") {
468
+ return;
469
+ }
470
+
471
+ // Only process string content
472
+ if (typeof message.content !== "string") {
473
+ return;
474
+ }
475
+ if (message?.tool_calls?.length) {
476
+ return;
477
+ }
478
+ const matches = this.detectXmlToolCalls(message.content);
479
+
480
+ let toolCalls: ToolCall[] = [];
481
+
482
+ if (matches.length === 0) {
483
+ // If no matches found with regex, try the simple string-based extractor first
484
+ const blocks = this.extractToolCallBlocks(message.content);
485
+
486
+ // If still no blocks found, try to detect incomplete tool calls
487
+ let allBlocks = blocks;
488
+ if (blocks.length === 0) {
489
+ allBlocks = this.detectIncompleteToolCalls(message.content);
490
+ }
491
+
492
+ toolCalls = allBlocks.map(block => {
493
+ return {
494
+ id: this.generateToolCallId(),
495
+ type: 'function' as const,
496
+ function: {
497
+ name: block.name,
498
+ arguments: block.arguments,
499
+ },
500
+ };
501
+ });
502
+ } else {
503
+ // Convert XML matches to proper tool calls using existing method
504
+ toolCalls = this.convertXmlToToolCalls(matches);
505
+ }
506
+
507
+ if (toolCalls.length === 0) {
508
+ return;
509
+ }
510
+
511
+ // Add tool calls to the message (merge with existing if any)
512
+ if (message.tool_calls) {
513
+ message.tool_calls.push(...toolCalls);
514
+ } else {
515
+ message.tool_calls = toolCalls;
516
+ }
517
+ }
518
+
519
+ /**
520
+ * Creates a message processor function for post_call processing
521
+ */
522
+ createProcessor(): MessageProcessorFunction {
523
+ return (originalMessages: Message[], modifiedMessages: Message[]): void => {
524
+ // Process each message in the modified messages array
525
+ for (const message of modifiedMessages) {
526
+ this.processMessage(message);
527
+ }
528
+ };
529
+ }
530
+ }
531
+
532
+ // Global instance for easy access
533
+ export const globalXmlToolCallProcessor = new XmlToolCallProcessor();
@@ -1,3 +1,6 @@
1
1
  export { Base64ImageDetector } from "./Base64ImageDetector";
2
+ export { CustomVariables } from "./CustomVariables";
2
3
  export { TokenCompressor } from "./TokenCompressor";
3
4
  export { ToolResponseCache } from "./ToolResponseCache";
5
+ export { XmlToolCallProcessor } from "./XmlToolCallProcessor";
6
+ export { HarmonyToolProcessor } from "./HarmonyToolProcessor";