@crownpeak/dqm-react-component-dev-mcp 1.2.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 (444) hide show
  1. package/README.md +138 -0
  2. package/data/.env.example +22 -0
  3. package/data/.gitattributes +47 -0
  4. package/data/.glfrc.json +7 -0
  5. package/data/.husky/pre-commit +5 -0
  6. package/data/.nvmrc +1 -0
  7. package/data/CHANGELOG.md +75 -0
  8. package/data/CODE_OF_CONDUCT.md +129 -0
  9. package/data/CONTRIBUTING.md +203 -0
  10. package/data/DOCS-STRUCTURE.md +307 -0
  11. package/data/I18N.md +292 -0
  12. package/data/LICENSE +22 -0
  13. package/data/README.md +315 -0
  14. package/data/SECURITY.md +125 -0
  15. package/data/WIKI-DEPLOYMENT.md +348 -0
  16. package/data/docs/AI-FEATURES.md +610 -0
  17. package/data/docs/API-REFERENCE.md +1022 -0
  18. package/data/docs/AUTHENTICATION.md +301 -0
  19. package/data/docs/BACKEND-API.md +468 -0
  20. package/data/docs/DEVELOPMENT.md +375 -0
  21. package/data/docs/EXAMPLES.md +622 -0
  22. package/data/docs/MCP-SERVER.md +307 -0
  23. package/data/docs/MIGRATION-GUIDE.md +367 -0
  24. package/data/docs/NPM-PUBLISH.md +193 -0
  25. package/data/docs/QUICKSTART.md +206 -0
  26. package/data/docs/REDIS-SETUP.md +162 -0
  27. package/data/docs/SERVER.md +228 -0
  28. package/data/docs/TROUBLESHOOTING.md +657 -0
  29. package/data/docs/WIDGET-GUIDE.md +638 -0
  30. package/data/docs/WIKI-HOME.md +58 -0
  31. package/data/docs/WIKI-SIDEBAR.md +39 -0
  32. package/data/package.json +171 -0
  33. package/data/playwright.config.ts +64 -0
  34. package/data/probe/.cargo/config.toml +10 -0
  35. package/data/probe/.claude/commands/performance-review.md +15 -0
  36. package/data/probe/.clinerules +288 -0
  37. package/data/probe/.dockerignore +57 -0
  38. package/data/probe/.githooks/post-commit +11 -0
  39. package/data/probe/.githooks/pre-commit +99 -0
  40. package/data/probe/.githooks/pre-commit-vow +9 -0
  41. package/data/probe/.prompts/engineer.md +41 -0
  42. package/data/probe/.roomodes +28 -0
  43. package/data/probe/.windsurfrules +0 -0
  44. package/data/probe/BASH_TOOL_SUMMARY.md +148 -0
  45. package/data/probe/BENCHMARKING.md +256 -0
  46. package/data/probe/CLAUDE.md +226 -0
  47. package/data/probe/CODE_OF_CONDUCT.md +128 -0
  48. package/data/probe/CONTRIBUTING.md +193 -0
  49. package/data/probe/Cargo.toml +120 -0
  50. package/data/probe/Cross.toml +10 -0
  51. package/data/probe/DOCKER-README.md +224 -0
  52. package/data/probe/Dockerfile +32 -0
  53. package/data/probe/ENHANCED_DEBUG_TELEMETRY.md +188 -0
  54. package/data/probe/LICENSE +201 -0
  55. package/data/probe/Makefile +210 -0
  56. package/data/probe/README.md +824 -0
  57. package/data/probe/SECURITY.md +67 -0
  58. package/data/probe/WINDOWS-GUIDE.md +294 -0
  59. package/data/probe/benches/parsing_benchmarks.rs +370 -0
  60. package/data/probe/benches/search_benchmarks.rs +599 -0
  61. package/data/probe/benches/simd_benchmarks.rs +372 -0
  62. package/data/probe/benches/timing_benchmarks.rs +287 -0
  63. package/data/probe/build-windows.bat +229 -0
  64. package/data/probe/codex-config/config.toml +6 -0
  65. package/data/probe/docs/PERFORMANCE_OPTIMIZATION.md +161 -0
  66. package/data/probe/examples/cache_demo.rs +46 -0
  67. package/data/probe/examples/chat/.dockerignore +37 -0
  68. package/data/probe/examples/chat/ChatSessionManager.js +295 -0
  69. package/data/probe/examples/chat/Dockerfile +98 -0
  70. package/data/probe/examples/chat/LICENSE +201 -0
  71. package/data/probe/examples/chat/LOCAL_IMAGE_SUPPORT.md +195 -0
  72. package/data/probe/examples/chat/MCP_INTEGRATION.md +400 -0
  73. package/data/probe/examples/chat/README.md +338 -0
  74. package/data/probe/examples/chat/TRACING.md +226 -0
  75. package/data/probe/examples/chat/appTracer.js +968 -0
  76. package/data/probe/examples/chat/auth.js +76 -0
  77. package/data/probe/examples/chat/bin/probe-chat.js +13 -0
  78. package/data/probe/examples/chat/build.js +104 -0
  79. package/data/probe/examples/chat/cancelRequest.js +84 -0
  80. package/data/probe/examples/chat/demo-agentic-image-flow.js +88 -0
  81. package/data/probe/examples/chat/demo-local-images.js +128 -0
  82. package/data/probe/examples/chat/fileSpanExporter.js +181 -0
  83. package/data/probe/examples/chat/implement/README.md +228 -0
  84. package/data/probe/examples/chat/implement/backends/AiderBackend.js +750 -0
  85. package/data/probe/examples/chat/implement/backends/BaseBackend.js +276 -0
  86. package/data/probe/examples/chat/implement/backends/ClaudeCodeBackend.js +767 -0
  87. package/data/probe/examples/chat/implement/backends/MockBackend.js +237 -0
  88. package/data/probe/examples/chat/implement/backends/registry.js +85 -0
  89. package/data/probe/examples/chat/implement/core/BackendManager.js +567 -0
  90. package/data/probe/examples/chat/implement/core/ImplementTool.js +354 -0
  91. package/data/probe/examples/chat/implement/core/config.js +428 -0
  92. package/data/probe/examples/chat/implement/core/timeouts.js +58 -0
  93. package/data/probe/examples/chat/implement/core/utils.js +496 -0
  94. package/data/probe/examples/chat/implement/types/BackendTypes.js +126 -0
  95. package/data/probe/examples/chat/index.js +669 -0
  96. package/data/probe/examples/chat/mcpServer.js +341 -0
  97. package/data/probe/examples/chat/npm/LICENSE +15 -0
  98. package/data/probe/examples/chat/npm/README.md +168 -0
  99. package/data/probe/examples/chat/npm/bin/probe-chat.js +156 -0
  100. package/data/probe/examples/chat/npm/index.js +259 -0
  101. package/data/probe/examples/chat/npm/package.json +54 -0
  102. package/data/probe/examples/chat/package.json +102 -0
  103. package/data/probe/examples/chat/probeChat.js +456 -0
  104. package/data/probe/examples/chat/probeTool.js +491 -0
  105. package/data/probe/examples/chat/storage/JsonChatStorage.js +476 -0
  106. package/data/probe/examples/chat/telemetry.js +281 -0
  107. package/data/probe/examples/chat/test/integration/chatFlows.test.js +320 -0
  108. package/data/probe/examples/chat/test/integration/toolCalling.test.js +471 -0
  109. package/data/probe/examples/chat/test/mocks/mockLLMProvider.js +269 -0
  110. package/data/probe/examples/chat/test/test-backends.js +90 -0
  111. package/data/probe/examples/chat/test/testUtils.js +530 -0
  112. package/data/probe/examples/chat/test/unit/backendTimeout.test.js +161 -0
  113. package/data/probe/examples/chat/test/unit/packageFiles.test.js +120 -0
  114. package/data/probe/examples/chat/test/verify-tests.js +118 -0
  115. package/data/probe/examples/chat/test-agentic-image-loading.js +294 -0
  116. package/data/probe/examples/chat/test-ai-sdk-telemetry.js +204 -0
  117. package/data/probe/examples/chat/test-chat-tracing.js +38 -0
  118. package/data/probe/examples/chat/test-direct-function.js +49 -0
  119. package/data/probe/examples/chat/test-file-size-validation.js +103 -0
  120. package/data/probe/examples/chat/test-full-mcp-integration.js +258 -0
  121. package/data/probe/examples/chat/test-github-context.txt +12 -0
  122. package/data/probe/examples/chat/test-hierarchy.js +203 -0
  123. package/data/probe/examples/chat/test-image-spans.js +37 -0
  124. package/data/probe/examples/chat/test-local-image-reading.js +176 -0
  125. package/data/probe/examples/chat/test-mcp-integration.js +136 -0
  126. package/data/probe/examples/chat/test-mcp-probe-server.js +161 -0
  127. package/data/probe/examples/chat/test-mcp-with-ai.js +279 -0
  128. package/data/probe/examples/chat/test-multiple-allowed-dirs.js +111 -0
  129. package/data/probe/examples/chat/test-probe-mcp-server.js +110 -0
  130. package/data/probe/examples/chat/test-security-validation.js +145 -0
  131. package/data/probe/examples/chat/test-simple-tracing.js +32 -0
  132. package/data/probe/examples/chat/test-trace-verification.js +235 -0
  133. package/data/probe/examples/chat/test-tracing.js +114 -0
  134. package/data/probe/examples/chat/tokenCounter.js +419 -0
  135. package/data/probe/examples/chat/tokenUsageDisplay.js +134 -0
  136. package/data/probe/examples/chat/webServer.js +1103 -0
  137. package/data/probe/examples/reranker/Cargo.toml +33 -0
  138. package/data/probe/examples/reranker/DEBUG_OUTPUT_ANALYSIS.md +71 -0
  139. package/data/probe/examples/reranker/MODELS.md +66 -0
  140. package/data/probe/examples/reranker/MODEL_COMPARISON.md +60 -0
  141. package/data/probe/examples/reranker/MULTI_MODEL_ANALYSIS.md +176 -0
  142. package/data/probe/examples/reranker/PERFORMANCE_SUMMARY.md +156 -0
  143. package/data/probe/examples/reranker/README.md +347 -0
  144. package/data/probe/examples/reranker/RUST_BERT_COMPARISON.md +82 -0
  145. package/data/probe/examples/reranker/TOKENIZATION_GUIDE.md +120 -0
  146. package/data/probe/examples/reranker/check_rust_tokenizer.py +108 -0
  147. package/data/probe/examples/reranker/convert_to_torchscript.py +109 -0
  148. package/data/probe/examples/reranker/debug_scoring.py +189 -0
  149. package/data/probe/examples/reranker/debug_tokenization.py +154 -0
  150. package/data/probe/examples/reranker/download_models.sh +73 -0
  151. package/data/probe/examples/reranker/requirements.txt +13 -0
  152. package/data/probe/examples/reranker/run_comprehensive_benchmark.sh +83 -0
  153. package/data/probe/examples/reranker/rust_bert_test/Cargo.toml +12 -0
  154. package/data/probe/examples/reranker/rust_bert_test/README.md +54 -0
  155. package/data/probe/examples/reranker/simple_test.py +50 -0
  156. package/data/probe/examples/reranker/test_all_models.sh +63 -0
  157. package/data/probe/examples/reranker/test_bert_results.sh +44 -0
  158. package/data/probe/examples/reranker/test_cross_encoder.py +334 -0
  159. package/data/probe/examples/reranker/test_cross_encoder.sh +80 -0
  160. package/data/probe/examples/reranker/test_exact_comparison.py +151 -0
  161. package/data/probe/examples/reranker/test_parallel_performance.sh +56 -0
  162. package/data/probe/examples/reranker/test_scores.py +132 -0
  163. package/data/probe/install.ps1 +508 -0
  164. package/data/probe/install.sh +460 -0
  165. package/data/probe/npm/CLONE_METHOD_EXAMPLES.md +596 -0
  166. package/data/probe/npm/CONTEXT_COMPACTION.md +303 -0
  167. package/data/probe/npm/DELEGATE_TOOL_README.md +166 -0
  168. package/data/probe/npm/MAID_INTEGRATION.md +313 -0
  169. package/data/probe/npm/MCP_INTEGRATION_SUMMARY.md +241 -0
  170. package/data/probe/npm/README.md +824 -0
  171. package/data/probe/npm/bin/.gitignore +7 -0
  172. package/data/probe/npm/bin/.gitkeep +0 -0
  173. package/data/probe/npm/bin/README.md +12 -0
  174. package/data/probe/npm/bin/probe +167 -0
  175. package/data/probe/npm/docs/CLAUDE_CODE_INTEGRATION.md +414 -0
  176. package/data/probe/npm/docs/CODEX_INTEGRATION.md +502 -0
  177. package/data/probe/npm/docs/EDIT_CREATE_TOOLS.md +233 -0
  178. package/data/probe/npm/docs/RETRY_AND_FALLBACK.md +674 -0
  179. package/data/probe/npm/example-usage.js +335 -0
  180. package/data/probe/npm/examples/multi-engine-demo.js +117 -0
  181. package/data/probe/npm/examples/probe-agent-cli.js +113 -0
  182. package/data/probe/npm/examples/test-agent-edit.js +114 -0
  183. package/data/probe/npm/examples/test-edit-create.js +120 -0
  184. package/data/probe/npm/examples/test-edit-direct.js +114 -0
  185. package/data/probe/npm/index.d.ts +744 -0
  186. package/data/probe/npm/jest.config.js +52 -0
  187. package/data/probe/npm/package.json +117 -0
  188. package/data/probe/npm/scripts/build-agent.cjs +75 -0
  189. package/data/probe/npm/scripts/build-cjs.js +124 -0
  190. package/data/probe/npm/scripts/build-mcp.cjs +36 -0
  191. package/data/probe/npm/scripts/postinstall.js +216 -0
  192. package/data/probe/npm/test-codex-e2e.js +78 -0
  193. package/data/probe/npm/test-download-lock.js +109 -0
  194. package/data/probe/npm/test-grep-security.js +94 -0
  195. package/data/probe/npm/test-grep-simplified.js +63 -0
  196. package/data/probe/npm/test-grep.js +51 -0
  197. package/data/probe/npm/tests/README.md +96 -0
  198. package/data/probe/npm/tests/agent-compact-history.test.js +174 -0
  199. package/data/probe/npm/tests/allow-tests-default.test.js +151 -0
  200. package/data/probe/npm/tests/contextCompactor.test.js +498 -0
  201. package/data/probe/npm/tests/delegate-config.test.js +353 -0
  202. package/data/probe/npm/tests/delegate-integration.test.js +348 -0
  203. package/data/probe/npm/tests/extractor-integration.test.js +162 -0
  204. package/data/probe/npm/tests/extractor.test.js +317 -0
  205. package/data/probe/npm/tests/fixtures/sampleDiagrams.js +267 -0
  206. package/data/probe/npm/tests/integration/claude-code-auto-fallback.spec.js +148 -0
  207. package/data/probe/npm/tests/integration/claude-code-multi-step.spec.js +127 -0
  208. package/data/probe/npm/tests/integration/claude-code-tool-events.spec.js +163 -0
  209. package/data/probe/npm/tests/integration/codex-auto-fallback.spec.js +191 -0
  210. package/data/probe/npm/tests/integration/codex-tool-events.spec.js +147 -0
  211. package/data/probe/npm/tests/integration/examplesChatMcp.test.js +402 -0
  212. package/data/probe/npm/tests/integration/mcpDotenvSupport.test.js +174 -0
  213. package/data/probe/npm/tests/integration/mcpErrorHandling.test.js +566 -0
  214. package/data/probe/npm/tests/integration/mcpRobustness.test.js +564 -0
  215. package/data/probe/npm/tests/integration/mcpStdoutPurity.test.js +355 -0
  216. package/data/probe/npm/tests/integration/probeAgentMcp.test.js +398 -0
  217. package/data/probe/npm/tests/integration/retryFallback.test.js +368 -0
  218. package/data/probe/npm/tests/integration/schema-in-initial-message.test.js +318 -0
  219. package/data/probe/npm/tests/integration/schema-validation-loop-prevention.test.js +244 -0
  220. package/data/probe/npm/tests/integration/schemaRetryLogic.test.js +94 -0
  221. package/data/probe/npm/tests/integration/validationFlow.test.js +329 -0
  222. package/data/probe/npm/tests/manual/test-codex-basic.js +110 -0
  223. package/data/probe/npm/tests/mcp/mcpClientManager.test.js +614 -0
  224. package/data/probe/npm/tests/mcp/mcpConfig.test.js +359 -0
  225. package/data/probe/npm/tests/mcp/mcpXmlBridge.test.js +436 -0
  226. package/data/probe/npm/tests/mcp/mockMcpServer.js +510 -0
  227. package/data/probe/npm/tests/mcp-strict-syntax.test.js +319 -0
  228. package/data/probe/npm/tests/mermaidQuoteEscaping.test.js +214 -0
  229. package/data/probe/npm/tests/nestedQuoteFix.test.js +40 -0
  230. package/data/probe/npm/tests/setup.js +46 -0
  231. package/data/probe/npm/tests/unit/allowed-tools.test.js +513 -0
  232. package/data/probe/npm/tests/unit/attempt-completion-closing-tag-in-content.test.js +188 -0
  233. package/data/probe/npm/tests/unit/attemptCompletionJsonFix.test.js +238 -0
  234. package/data/probe/npm/tests/unit/attemptCompletionJsonIssue.test.js +128 -0
  235. package/data/probe/npm/tests/unit/backtickAutoFix.test.js +35 -0
  236. package/data/probe/npm/tests/unit/bash-probe-agent-integration.test.js +389 -0
  237. package/data/probe/npm/tests/unit/bash-simple-commands.test.js +324 -0
  238. package/data/probe/npm/tests/unit/bash-tool-comprehensive.test.js +371 -0
  239. package/data/probe/npm/tests/unit/bash-tool-integration.test.js +310 -0
  240. package/data/probe/npm/tests/unit/bash-tool.test.js +341 -0
  241. package/data/probe/npm/tests/unit/completion-prompt.test.js +379 -0
  242. package/data/probe/npm/tests/unit/cwd-path-options.test.js +287 -0
  243. package/data/probe/npm/tests/unit/delegate-limits.test.js +422 -0
  244. package/data/probe/npm/tests/unit/direct-content-attempt-completion.test.js +235 -0
  245. package/data/probe/npm/tests/unit/edit-create-tools.test.js +609 -0
  246. package/data/probe/npm/tests/unit/enhancedMermaidValidation.test.js +577 -0
  247. package/data/probe/npm/tests/unit/extract-content.test.js +83 -0
  248. package/data/probe/npm/tests/unit/extract-multiple-targets.test.js +89 -0
  249. package/data/probe/npm/tests/unit/fallbackManager.test.js +442 -0
  250. package/data/probe/npm/tests/unit/githubCompatibilityValidation.test.js +258 -0
  251. package/data/probe/npm/tests/unit/imageConfig.test.js +149 -0
  252. package/data/probe/npm/tests/unit/imagePathResolution.test.js +345 -0
  253. package/data/probe/npm/tests/unit/json-fixing-agent.test.js +238 -0
  254. package/data/probe/npm/tests/unit/json-validation-enhanced-errors.test.js +199 -0
  255. package/data/probe/npm/tests/unit/jsonValidationInfiniteLoopFix.test.js +228 -0
  256. package/data/probe/npm/tests/unit/maidIntegration.test.js +139 -0
  257. package/data/probe/npm/tests/unit/maxIterationsWarning.test.js +195 -0
  258. package/data/probe/npm/tests/unit/mermaidEdgeLabelFix.test.js +161 -0
  259. package/data/probe/npm/tests/unit/mermaidHtmlEntities.test.js +76 -0
  260. package/data/probe/npm/tests/unit/mermaidInfiniteLoopFix.test.js +64 -0
  261. package/data/probe/npm/tests/unit/mermaidValidation.test.js +723 -0
  262. package/data/probe/npm/tests/unit/mermaidValidationVisorExample.test.js +309 -0
  263. package/data/probe/npm/tests/unit/probe-agent-clone-realistic.test.js +643 -0
  264. package/data/probe/npm/tests/unit/probe-agent-clone.test.js +476 -0
  265. package/data/probe/npm/tests/unit/probe-agent-delegate.test.js +400 -0
  266. package/data/probe/npm/tests/unit/probe-agent-model-option.test.js +118 -0
  267. package/data/probe/npm/tests/unit/probeTool-security.test.js +283 -0
  268. package/data/probe/npm/tests/unit/readImageTool.test.js +418 -0
  269. package/data/probe/npm/tests/unit/retryManager.test.js +317 -0
  270. package/data/probe/npm/tests/unit/schema-aware-reminders.test.js +288 -0
  271. package/data/probe/npm/tests/unit/schemaDefinitionDetection.test.js +115 -0
  272. package/data/probe/npm/tests/unit/schemaUtils.test.js +1268 -0
  273. package/data/probe/npm/tests/unit/simpleTelemetry.test.js +282 -0
  274. package/data/probe/npm/tests/unit/simplified-attempt-completion.test.js +274 -0
  275. package/data/probe/npm/tests/unit/single-quote-json-bug.test.js +231 -0
  276. package/data/probe/npm/tests/unit/subgraphAutoFix.test.js +110 -0
  277. package/data/probe/npm/tests/unit/system-prompt.test.js +32 -0
  278. package/data/probe/npm/tests/unit/types-probe-agent-options.test.js +42 -0
  279. package/data/probe/npm/tests/unit/xmlParsing.test.js +720 -0
  280. package/data/probe/npm/tsconfig.json +21 -0
  281. package/data/probe/result1.txt +19 -0
  282. package/data/probe/result2.txt +26 -0
  283. package/data/probe/scripts/benchmark.sh +270 -0
  284. package/data/probe/scripts/cache_memory_analysis.rs +844 -0
  285. package/data/probe/scripts/claude-hook-wrapper.sh +56 -0
  286. package/data/probe/site/.env.example +10 -0
  287. package/data/probe/site/DEPLOYMENT.md +86 -0
  288. package/data/probe/site/README.md +183 -0
  289. package/data/probe/site/adding-languages.md +135 -0
  290. package/data/probe/site/ai-chat.md +427 -0
  291. package/data/probe/site/ai-integration.md +1488 -0
  292. package/data/probe/site/blog/agentic-flow-custom-xml-protocol.md +407 -0
  293. package/data/probe/site/blog/index.md +118 -0
  294. package/data/probe/site/blog/v0.6.0-release.md +426 -0
  295. package/data/probe/site/blog.md +8 -0
  296. package/data/probe/site/changelog.md +200 -0
  297. package/data/probe/site/cli-mode.md +437 -0
  298. package/data/probe/site/code-extraction.md +436 -0
  299. package/data/probe/site/contributing/README.md +9 -0
  300. package/data/probe/site/contributing/documentation-cross-references.md +215 -0
  301. package/data/probe/site/contributing/documentation-maintenance.md +275 -0
  302. package/data/probe/site/contributing/documentation-structure.md +75 -0
  303. package/data/probe/site/documentation-cross-references.md +215 -0
  304. package/data/probe/site/documentation-guide.md +132 -0
  305. package/data/probe/site/documentation-maintenance.md +275 -0
  306. package/data/probe/site/features.md +147 -0
  307. package/data/probe/site/how-it-works.md +118 -0
  308. package/data/probe/site/index.md +175 -0
  309. package/data/probe/site/index.md.bak +133 -0
  310. package/data/probe/site/installation.md +235 -0
  311. package/data/probe/site/integrations/docker.md +248 -0
  312. package/data/probe/site/integrations/github-actions.md +413 -0
  313. package/data/probe/site/language-support-overview.md +168 -0
  314. package/data/probe/site/mcp-integration.md +587 -0
  315. package/data/probe/site/mcp-server.md +304 -0
  316. package/data/probe/site/navigation-structure.md +76 -0
  317. package/data/probe/site/nodejs-sdk.md +798 -0
  318. package/data/probe/site/output-formats.md +625 -0
  319. package/data/probe/site/package.json +21 -0
  320. package/data/probe/site/public/_headers +28 -0
  321. package/data/probe/site/public/_redirects +11 -0
  322. package/data/probe/site/quick-start.md +289 -0
  323. package/data/probe/site/search-functionality.md +291 -0
  324. package/data/probe/site/search-reference.md +291 -0
  325. package/data/probe/site/supported-languages.md +215 -0
  326. package/data/probe/site/use-cases/README.md +8 -0
  327. package/data/probe/site/use-cases/advanced-cli.md +253 -0
  328. package/data/probe/site/use-cases/ai-code-editors.md +239 -0
  329. package/data/probe/site/use-cases/building-ai-tools.md +529 -0
  330. package/data/probe/site/use-cases/cli-ai-workflows.md +285 -0
  331. package/data/probe/site/use-cases/deploying-probe-web-interface.md +255 -0
  332. package/data/probe/site/use-cases/integrating-probe-into-ai-code-editors.md +161 -0
  333. package/data/probe/site/use-cases/nodejs-sdk.md +596 -0
  334. package/data/probe/site/use-cases/team-chat.md +350 -0
  335. package/data/probe/site/web-interface.md +434 -0
  336. package/data/probe/site/wrangler.toml +9 -0
  337. package/data/probe/test-api-key.sh +1 -0
  338. package/data/probe/test-probe-implementation/hello.js +7 -0
  339. package/data/probe/test_cases/demonstrate_early_termination_issues.sh +176 -0
  340. package/data/probe/test_cases/early_termination_issues.rs +533 -0
  341. package/data/probe/test_data/test_nested_struct.go +26 -0
  342. package/data/probe/tests/README.md +286 -0
  343. package/data/probe/tests/README_search_determinism_tests.md +116 -0
  344. package/data/probe/tests/adjacent_comment_test.rs +152 -0
  345. package/data/probe/tests/apostrophe_handling_tests.rs +132 -0
  346. package/data/probe/tests/block_filtering_with_ast_tests.rs +669 -0
  347. package/data/probe/tests/block_merging_tests.rs +396 -0
  348. package/data/probe/tests/c_outline_format_tests.rs +2179 -0
  349. package/data/probe/tests/cache_invalidation_issues.rs.disabled +682 -0
  350. package/data/probe/tests/cache_order_tests.rs +147 -0
  351. package/data/probe/tests/cache_query_scoping_tests.rs +221 -0
  352. package/data/probe/tests/cli_tests.rs +680 -0
  353. package/data/probe/tests/comment_context_integration_test.rs +240 -0
  354. package/data/probe/tests/common.rs +33 -0
  355. package/data/probe/tests/complex_block_merging_tests.rs +599 -0
  356. package/data/probe/tests/complex_query_block_filtering_tests.rs +422 -0
  357. package/data/probe/tests/control_flow_closing_braces_test.rs +91 -0
  358. package/data/probe/tests/cpp_outline_format_tests.rs +1507 -0
  359. package/data/probe/tests/csharp_outline_format_tests.rs +941 -0
  360. package/data/probe/tests/elastic_query_integration_tests.rs +922 -0
  361. package/data/probe/tests/extract_command_tests.rs +1848 -0
  362. package/data/probe/tests/extract_deduplication_tests.rs +146 -0
  363. package/data/probe/tests/extract_input_file_tests.rs +84 -0
  364. package/data/probe/tests/extract_prompt_tests.rs +102 -0
  365. package/data/probe/tests/filename_search_tests.rs +96 -0
  366. package/data/probe/tests/fixtures/user/AssemblyInfo.cs +3 -0
  367. package/data/probe/tests/github_extract_tests.rs +234 -0
  368. package/data/probe/tests/go_comment_test.rs +253 -0
  369. package/data/probe/tests/go_outline_format_tests.rs +2587 -0
  370. package/data/probe/tests/go_path_resolver_tests.rs +96 -0
  371. package/data/probe/tests/html_outline_format_tests.rs +637 -0
  372. package/data/probe/tests/integration_tests.rs +837 -0
  373. package/data/probe/tests/ip_whitelist_test.rs +148 -0
  374. package/data/probe/tests/java_outline_format_tests.rs +1611 -0
  375. package/data/probe/tests/javascript_extract_tests.rs +315 -0
  376. package/data/probe/tests/javascript_outline_format_tests.rs +1464 -0
  377. package/data/probe/tests/json_format_tests.rs +436 -0
  378. package/data/probe/tests/json_schema_validation_tests.rs +450 -0
  379. package/data/probe/tests/lib_usage.rs +60 -0
  380. package/data/probe/tests/line_comment_context_extension_test.rs +459 -0
  381. package/data/probe/tests/line_map_cache_tests.rs +114 -0
  382. package/data/probe/tests/markdown_integration_tests.rs +190 -0
  383. package/data/probe/tests/mocks/test_ip_whitelist.go +11 -0
  384. package/data/probe/tests/mocks/test_object.js +27 -0
  385. package/data/probe/tests/mocks/test_struct.go +50 -0
  386. package/data/probe/tests/multi_keyword_pattern_tests.rs +464 -0
  387. package/data/probe/tests/multi_language_syntax_integration_tests.rs +218 -0
  388. package/data/probe/tests/multiple_capture_groups_tests.rs +169 -0
  389. package/data/probe/tests/negative_compound_word_tests.rs +246 -0
  390. package/data/probe/tests/nested_symbol_extraction_tests.rs +99 -0
  391. package/data/probe/tests/outline_cross_file_interference_test.rs +335 -0
  392. package/data/probe/tests/outline_keyword_preservation_test.rs +67 -0
  393. package/data/probe/tests/output_format_edge_cases_tests.rs +693 -0
  394. package/data/probe/tests/parallel_extraction_tests.rs +178 -0
  395. package/data/probe/tests/parallel_search_tests.rs +355 -0
  396. package/data/probe/tests/path_resolver_tests.rs +698 -0
  397. package/data/probe/tests/php_outline_format_extended_tests.rs +928 -0
  398. package/data/probe/tests/php_outline_format_tests.rs +768 -0
  399. package/data/probe/tests/property_tests.proptest-regressions +9 -0
  400. package/data/probe/tests/property_tests.rs +118 -0
  401. package/data/probe/tests/python_outline_format_tests.rs +1538 -0
  402. package/data/probe/tests/query_command_json_tests.rs +438 -0
  403. package/data/probe/tests/query_command_tests.rs +232 -0
  404. package/data/probe/tests/query_command_xml_tests.rs +569 -0
  405. package/data/probe/tests/quoted_term_with_negative_keyword_tests.rs +216 -0
  406. package/data/probe/tests/required_terms_filename_tests.rs +116 -0
  407. package/data/probe/tests/ruby_outline_format_tests.rs +1011 -0
  408. package/data/probe/tests/rust_line_comment_context_test.rs +151 -0
  409. package/data/probe/tests/rust_outline_format_enhanced_tests.rs +725 -0
  410. package/data/probe/tests/rust_outline_format_tests.rs +843 -0
  411. package/data/probe/tests/schemas/xml_output_schema.xsd +38 -0
  412. package/data/probe/tests/search_determinism_tests.rs +451 -0
  413. package/data/probe/tests/search_hints_tests.rs +253 -0
  414. package/data/probe/tests/special_character_escaping_tests.rs +417 -0
  415. package/data/probe/tests/stemming_compound_word_filtering_tests.rs +535 -0
  416. package/data/probe/tests/strict_elastic_syntax_tests.rs +404 -0
  417. package/data/probe/tests/swift_outline_format_tests.rs +3319 -0
  418. package/data/probe/tests/symbols_tests.rs +166 -0
  419. package/data/probe/tests/test_file.rs +45 -0
  420. package/data/probe/tests/test_tokenize.rs +28 -0
  421. package/data/probe/tests/timeout_tests.rs +82 -0
  422. package/data/probe/tests/tokenization_tests.rs +195 -0
  423. package/data/probe/tests/tokenized_block_filtering_tests.rs +174 -0
  424. package/data/probe/tests/typescript_extract_tests.rs +214 -0
  425. package/data/probe/tests/typescript_outline_format_tests.rs +2188 -0
  426. package/data/probe/tests/xml_format_tests.rs +568 -0
  427. package/data/probe/tests/xml_schema_validation_tests.rs +497 -0
  428. package/data/scripts/postinstall.mjs +9 -0
  429. package/data/scripts/set-version.js +0 -0
  430. package/data/scripts/wiki-build.sh +111 -0
  431. package/data/scripts/wiki-deploy.sh +73 -0
  432. package/data/serve.json +12 -0
  433. package/data/test/demo-dynamic.html +134 -0
  434. package/data/test/demo-esm.html +105 -0
  435. package/data/test/demo-iife.html +78 -0
  436. package/data/tsconfig.json +7 -0
  437. package/data/vite.server.ts +483 -0
  438. package/data/vitest.config.ts +40 -0
  439. package/data/wiki/Home.md +58 -0
  440. package/data/wiki/_Sidebar.md +39 -0
  441. package/docs-mcp.config.json +20 -0
  442. package/package.json +56 -0
  443. package/src/config.js +111 -0
  444. package/src/index.js +395 -0
@@ -0,0 +1,38 @@
1
+ <?xml version="1.0" encoding="UTF-8"?>
2
+ <xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema">
3
+ <xs:element name="probe_results">
4
+ <xs:complexType>
5
+ <xs:sequence>
6
+ <xs:element name="result" minOccurs="0" maxOccurs="unbounded">
7
+ <xs:complexType>
8
+ <xs:sequence>
9
+ <xs:element name="file" type="xs:string"/>
10
+ <xs:element name="lines" type="xs:string"/>
11
+ <xs:element name="node_type" type="xs:string"/>
12
+ <xs:element name="column_start" type="xs:integer" minOccurs="0"/>
13
+ <xs:element name="column_end" type="xs:integer" minOccurs="0"/>
14
+ <xs:element name="code" type="xs:string"/>
15
+ <xs:element name="matched_keywords" minOccurs="0">
16
+ <xs:complexType>
17
+ <xs:sequence>
18
+ <xs:element name="keyword" type="xs:string" minOccurs="0" maxOccurs="unbounded"/>
19
+ </xs:sequence>
20
+ </xs:complexType>
21
+ </xs:element>
22
+ <xs:element name="score" type="xs:decimal" minOccurs="0"/>
23
+ </xs:sequence>
24
+ </xs:complexType>
25
+ </xs:element>
26
+ <xs:element name="summary">
27
+ <xs:complexType>
28
+ <xs:sequence>
29
+ <xs:element name="count" type="xs:nonNegativeInteger"/>
30
+ <xs:element name="total_bytes" type="xs:nonNegativeInteger"/>
31
+ <xs:element name="total_tokens" type="xs:nonNegativeInteger"/>
32
+ </xs:sequence>
33
+ </xs:complexType>
34
+ </xs:element>
35
+ </xs:sequence>
36
+ </xs:complexType>
37
+ </xs:element>
38
+ </xs:schema>
@@ -0,0 +1,451 @@
1
+ use std::collections::HashMap;
2
+ use std::env;
3
+ use std::path::PathBuf;
4
+ use std::process::Command;
5
+
6
+ /// This test reproduces non-deterministic search behavior where the same query
7
+ /// returns different results on repeated executions.
8
+ ///
9
+ /// **Issue Description:**
10
+ /// The command `probe search "yaml workflow agent multi-agent user input" [path containing "user"]`
11
+ /// returns inconsistent results:
12
+ /// - Sometimes: Lines 1-3 with content (115 bytes, 33 tokens)
13
+ /// - Sometimes: Lines 1-4 with empty content (0 bytes, 0 tokens)
14
+ ///
15
+ /// **Hypothesis:** The issue may be related to filename matching vs content matching,
16
+ /// especially when the search path contains the keyword "user" from the query.
17
+ #[test]
18
+ fn test_search_determinism_with_user_path() {
19
+ let iterations = 50; // Run more times to catch non-determinism
20
+ let mut results: Vec<SearchResult> = Vec::new();
21
+
22
+ // Get the path to the compiled binary
23
+ let cargo_target_dir = env::var("CARGO_TARGET_DIR").unwrap_or_else(|_| "target".to_string());
24
+ let binary_path = PathBuf::from(&cargo_target_dir)
25
+ .join("release")
26
+ .join("probe");
27
+
28
+ // If release binary doesn't exist, try debug
29
+ let binary_path = if binary_path.exists() {
30
+ binary_path
31
+ } else {
32
+ PathBuf::from(&cargo_target_dir).join("debug").join("probe")
33
+ };
34
+
35
+ // Path to test fixture - importantly contains "user" keyword
36
+ let fixture_path = PathBuf::from(env!("CARGO_MANIFEST_DIR"))
37
+ .join("tests")
38
+ .join("fixtures")
39
+ .join("user");
40
+
41
+ println!("Testing search determinism with {iterations} iterations");
42
+ println!("Binary path: {binary_path:?}");
43
+ println!("Fixture path: {fixture_path:?}");
44
+ println!("Query: \"yaml workflow agent multi-agent user input\"");
45
+ println!("Expected consistent results across all runs\n");
46
+
47
+ // Test specifically with --no-merge flag since we've identified it causes non-determinism
48
+ let use_no_merge = true;
49
+
50
+ // Run the same search multiple times
51
+ for i in 1..=iterations {
52
+ let mut cmd = Command::new(&binary_path);
53
+ cmd.args([
54
+ "search",
55
+ "yaml workflow agent multi-agent user input",
56
+ fixture_path.to_str().unwrap(),
57
+ ]);
58
+
59
+ if use_no_merge {
60
+ cmd.arg("--no-merge");
61
+ }
62
+
63
+ let output = cmd.output().expect("Failed to execute probe command");
64
+
65
+ if !output.status.success() {
66
+ let stderr = String::from_utf8_lossy(&output.stderr);
67
+ panic!("Command failed on iteration {i}: {stderr}");
68
+ }
69
+
70
+ let stdout = String::from_utf8_lossy(&output.stdout);
71
+ let result = parse_search_output(&stdout);
72
+
73
+ println!(
74
+ "Iteration {}: {} lines, {} bytes, {} tokens",
75
+ i, result.line_count, result.byte_count, result.token_count
76
+ );
77
+
78
+ results.push(result);
79
+ }
80
+
81
+ // Analyze results for consistency
82
+ let mut unique_results: HashMap<String, usize> = HashMap::new();
83
+
84
+ for result in &results {
85
+ let key = format!(
86
+ "{}:{}:{}",
87
+ result.line_count, result.byte_count, result.token_count
88
+ );
89
+ *unique_results.entry(key).or_insert(0) += 1;
90
+ }
91
+
92
+ println!("\n=== DETERMINISM ANALYSIS ===");
93
+ println!("Unique result patterns found:");
94
+ for (pattern, count) in &unique_results {
95
+ println!(" {pattern}: {count} occurrences");
96
+ }
97
+
98
+ // Test assertion: All results should be identical
99
+ if unique_results.len() > 1 {
100
+ println!("\n❌ NON-DETERMINISTIC BEHAVIOR DETECTED!");
101
+ println!("Expected: All {iterations} iterations to return identical results");
102
+ println!(
103
+ "Actual: Found {} different result patterns",
104
+ unique_results.len()
105
+ );
106
+
107
+ // Print detailed comparison of first few different results
108
+ let first_result = &results[0];
109
+ for (i, result) in results.iter().enumerate().skip(1) {
110
+ if !results_equal(first_result, result) {
111
+ println!("\nDifference detected:");
112
+ println!(
113
+ " Iteration 1: {} lines, {} bytes, {} tokens",
114
+ first_result.line_count, first_result.byte_count, first_result.token_count
115
+ );
116
+ println!(
117
+ " Iteration {}: {} lines, {} bytes, {} tokens",
118
+ i + 1,
119
+ result.line_count,
120
+ result.byte_count,
121
+ result.token_count
122
+ );
123
+ break;
124
+ }
125
+ }
126
+
127
+ panic!("Search results are non-deterministic! Found {} different result patterns. This indicates a bug in the search engine that needs to be fixed.", unique_results.len());
128
+ } else {
129
+ println!("\n✅ DETERMINISTIC BEHAVIOR CONFIRMED");
130
+ println!("All {iterations} iterations returned identical results");
131
+ let first_result = &results[0];
132
+ println!(
133
+ "Consistent result: {} lines, {} bytes, {} tokens",
134
+ first_result.line_count, first_result.byte_count, first_result.token_count
135
+ );
136
+ }
137
+ }
138
+
139
+ /// Test specifically for the filename vs content matching hypothesis
140
+ #[test]
141
+ fn test_user_keyword_filename_vs_content_matching() {
142
+ let cargo_target_dir = env::var("CARGO_TARGET_DIR").unwrap_or_else(|_| "target".to_string());
143
+ let binary_path = PathBuf::from(&cargo_target_dir)
144
+ .join("release")
145
+ .join("probe");
146
+
147
+ let binary_path = if binary_path.exists() {
148
+ binary_path
149
+ } else {
150
+ PathBuf::from(&cargo_target_dir).join("debug").join("probe")
151
+ };
152
+
153
+ let fixture_path = PathBuf::from(env!("CARGO_MANIFEST_DIR"))
154
+ .join("tests")
155
+ .join("fixtures")
156
+ .join("user");
157
+
158
+ println!("Testing filename vs content matching hypothesis");
159
+ println!("Path contains 'user' keyword: {fixture_path:?}");
160
+ println!("Query contains 'user' keyword: \"yaml workflow agent multi-agent user input\"");
161
+ println!("File content does NOT contain these keywords (AssemblyInfo.cs has only copyright and assembly info)\n");
162
+
163
+ // Run a single search to see what happens
164
+ let output = Command::new(&binary_path)
165
+ .args([
166
+ "search",
167
+ "yaml workflow agent multi-agent user input",
168
+ fixture_path.to_str().unwrap(),
169
+ ])
170
+ .output()
171
+ .expect("Failed to execute probe command");
172
+
173
+ if !output.status.success() {
174
+ let stderr = String::from_utf8_lossy(&output.stderr);
175
+ panic!("Command failed: {stderr}");
176
+ }
177
+
178
+ let stdout = String::from_utf8_lossy(&output.stdout);
179
+ let result = parse_search_output(&stdout);
180
+
181
+ println!(
182
+ "Search result: {} lines, {} bytes, {} tokens",
183
+ result.line_count, result.byte_count, result.token_count
184
+ );
185
+ println!("Raw output:\n{stdout}");
186
+
187
+ // This test documents the behavior - it may return results due to filename matching
188
+ // even though the content doesn't contain the search terms
189
+ if result.line_count > 0 {
190
+ println!("\n📝 OBSERVATION: Search returned results despite content mismatch");
191
+ println!("This suggests filename/path matching is contributing to results");
192
+ } else {
193
+ println!("\n📝 OBSERVATION: Search returned no results, suggesting content-only matching");
194
+ }
195
+ }
196
+
197
+ /// Test for non-deterministic behavior with different ranking algorithms and concurrent execution
198
+ #[test]
199
+ fn test_search_determinism_with_multiple_conditions() {
200
+ let cargo_target_dir = env::var("CARGO_TARGET_DIR").unwrap_or_else(|_| "target".to_string());
201
+ let binary_path = PathBuf::from(&cargo_target_dir)
202
+ .join("release")
203
+ .join("probe");
204
+
205
+ let binary_path = if binary_path.exists() {
206
+ binary_path
207
+ } else {
208
+ PathBuf::from(&cargo_target_dir).join("debug").join("probe")
209
+ };
210
+
211
+ let fixture_path = PathBuf::from(env!("CARGO_MANIFEST_DIR"))
212
+ .join("tests")
213
+ .join("fixtures")
214
+ .join("user");
215
+
216
+ println!("Testing multiple conditions that might trigger non-determinism");
217
+
218
+ // Test different search configurations that might trigger non-determinism
219
+ let search_configs = vec![
220
+ ("default", vec![]),
221
+ ("exact", vec!["--exact"]),
222
+ ("frequency", vec!["--frequency"]),
223
+ ("no-merge", vec!["--no-merge"]),
224
+ ("files-only", vec!["--files-only"]),
225
+ ("exclude-filenames", vec!["--exclude-filenames"]),
226
+ ];
227
+
228
+ for (name, config_flags) in search_configs {
229
+ println!("\n--- Testing with {name} configuration ---");
230
+ let mut results = Vec::new();
231
+
232
+ // Run multiple times with this configuration
233
+ for i in 1..=10 {
234
+ let mut cmd = Command::new(&binary_path);
235
+ cmd.args([
236
+ "search",
237
+ "yaml workflow agent multi-agent user input",
238
+ fixture_path.to_str().unwrap(),
239
+ ]);
240
+
241
+ // Add configuration flags
242
+ for flag in &config_flags {
243
+ cmd.arg(flag);
244
+ }
245
+
246
+ let output = cmd.output().expect("Failed to execute probe command");
247
+
248
+ if !output.status.success() {
249
+ let stderr = String::from_utf8_lossy(&output.stderr);
250
+ panic!("Command failed on iteration {i} with {name}: {stderr}");
251
+ }
252
+
253
+ let stdout = String::from_utf8_lossy(&output.stdout);
254
+ let result = parse_search_output(&stdout);
255
+ results.push(result);
256
+ }
257
+
258
+ // Check for consistency within this configuration
259
+ let first_result = &results[0];
260
+ let mut inconsistent = false;
261
+
262
+ for (i, result) in results.iter().enumerate().skip(1) {
263
+ if !results_equal(first_result, result) {
264
+ println!("❌ INCONSISTENCY DETECTED with {name} configuration!");
265
+ println!(
266
+ " Iteration 1: {} lines, {} bytes, {} tokens",
267
+ first_result.line_count, first_result.byte_count, first_result.token_count
268
+ );
269
+ println!(
270
+ " Iteration {}: {} lines, {} bytes, {} tokens",
271
+ i + 1,
272
+ result.line_count,
273
+ result.byte_count,
274
+ result.token_count
275
+ );
276
+ inconsistent = true;
277
+ break;
278
+ }
279
+ }
280
+
281
+ if !inconsistent {
282
+ println!(
283
+ "✅ {} configuration is consistent: {} lines, {} bytes, {} tokens",
284
+ name, first_result.line_count, first_result.byte_count, first_result.token_count
285
+ );
286
+ } else {
287
+ // Fail the test if we detect non-deterministic behavior
288
+ panic!("Non-deterministic behavior detected with {name} configuration! This needs to be fixed.");
289
+ }
290
+ }
291
+ }
292
+
293
+ /// Test for race conditions by running multiple searches concurrently
294
+ #[test]
295
+ fn test_search_determinism_concurrent_execution() {
296
+ use std::sync::mpsc;
297
+ use std::thread;
298
+
299
+ let cargo_target_dir = env::var("CARGO_TARGET_DIR").unwrap_or_else(|_| "target".to_string());
300
+ let binary_path = PathBuf::from(&cargo_target_dir)
301
+ .join("release")
302
+ .join("probe");
303
+
304
+ let binary_path = if binary_path.exists() {
305
+ binary_path
306
+ } else {
307
+ PathBuf::from(&cargo_target_dir).join("debug").join("probe")
308
+ };
309
+
310
+ let fixture_path = PathBuf::from(env!("CARGO_MANIFEST_DIR"))
311
+ .join("tests")
312
+ .join("fixtures")
313
+ .join("user");
314
+
315
+ println!("Testing concurrent execution for race conditions");
316
+
317
+ let (tx, rx) = mpsc::channel();
318
+ let thread_count = 10;
319
+
320
+ // Spawn multiple threads running the same search
321
+ for thread_id in 0..thread_count {
322
+ let tx = tx.clone();
323
+ let binary_path = binary_path.clone();
324
+ let fixture_path = fixture_path.clone();
325
+
326
+ thread::spawn(move || {
327
+ let output = Command::new(&binary_path)
328
+ .args([
329
+ "search",
330
+ "yaml workflow agent multi-agent user input",
331
+ fixture_path.to_str().unwrap(),
332
+ ])
333
+ .output()
334
+ .expect("Failed to execute probe command");
335
+
336
+ if !output.status.success() {
337
+ let stderr = String::from_utf8_lossy(&output.stderr);
338
+ panic!("Command failed in thread {thread_id}: {stderr}");
339
+ }
340
+
341
+ let stdout = String::from_utf8_lossy(&output.stdout);
342
+ let result = parse_search_output(&stdout);
343
+ tx.send((thread_id, result)).unwrap();
344
+ });
345
+ }
346
+
347
+ // Collect results from all threads
348
+ drop(tx); // Close the sender
349
+ let mut results: Vec<(usize, SearchResult)> = rx.iter().collect();
350
+ results.sort_by_key(|(thread_id, _)| *thread_id);
351
+
352
+ println!("Concurrent execution results:");
353
+ for (thread_id, result) in &results {
354
+ println!(
355
+ " Thread {}: {} lines, {} bytes, {} tokens",
356
+ thread_id, result.line_count, result.byte_count, result.token_count
357
+ );
358
+ }
359
+
360
+ // Check for consistency across threads
361
+ let first_result = &results[0].1;
362
+ let mut inconsistent = false;
363
+
364
+ for (thread_id, result) in results.iter().skip(1) {
365
+ if !results_equal(first_result, result) {
366
+ println!("❌ RACE CONDITION DETECTED!");
367
+ println!(
368
+ " Thread 0: {} lines, {} bytes, {} tokens",
369
+ first_result.line_count, first_result.byte_count, first_result.token_count
370
+ );
371
+ println!(
372
+ " Thread {}: {} lines, {} bytes, {} tokens",
373
+ thread_id, result.line_count, result.byte_count, result.token_count
374
+ );
375
+ inconsistent = true;
376
+ break;
377
+ }
378
+ }
379
+
380
+ if !inconsistent {
381
+ println!(
382
+ "✅ Concurrent execution is consistent: {} lines, {} bytes, {} tokens",
383
+ first_result.line_count, first_result.byte_count, first_result.token_count
384
+ );
385
+ }
386
+
387
+ // This test documents behavior but doesn't fail - race conditions are hard to reproduce reliably
388
+ }
389
+
390
+ #[derive(Debug, Clone)]
391
+ struct SearchResult {
392
+ line_count: u32,
393
+ byte_count: u32,
394
+ token_count: u32,
395
+ #[allow(dead_code)]
396
+ content: String,
397
+ }
398
+
399
+ fn parse_search_output(output: &str) -> SearchResult {
400
+ let mut line_count = 0;
401
+ let mut byte_count = 0;
402
+ let mut token_count = 0;
403
+ let mut content = String::new();
404
+
405
+ // Look for summary lines
406
+ for line in output.lines() {
407
+ // New format: "Total bytes returned: X"
408
+ if line.starts_with("Total bytes returned:") {
409
+ if let Some(bytes_str) = line.split(':').nth(1) {
410
+ if let Ok(bytes) = bytes_str.trim().parse::<u32>() {
411
+ byte_count = bytes;
412
+ }
413
+ }
414
+ }
415
+
416
+ // New format: "Total tokens returned: X"
417
+ if line.starts_with("Total tokens returned:") {
418
+ if let Some(tokens_str) = line.split(':').nth(1) {
419
+ if let Ok(tokens) = tokens_str.trim().parse::<u32>() {
420
+ token_count = tokens;
421
+ }
422
+ }
423
+ }
424
+
425
+ // Count lines in code blocks (Lines: X-Y format)
426
+ if line.starts_with("Lines:") {
427
+ if let Some(range_str) = line.strip_prefix("Lines: ") {
428
+ if let Some((start_str, end_str)) = range_str.split_once('-') {
429
+ if let (Ok(start), Ok(end)) = (start_str.parse::<u32>(), end_str.parse::<u32>())
430
+ {
431
+ line_count = end - start + 1;
432
+ }
433
+ }
434
+ }
435
+ }
436
+
437
+ content.push_str(line);
438
+ content.push('\n');
439
+ }
440
+
441
+ SearchResult {
442
+ line_count,
443
+ byte_count,
444
+ token_count,
445
+ content,
446
+ }
447
+ }
448
+
449
+ fn results_equal(a: &SearchResult, b: &SearchResult) -> bool {
450
+ a.line_count == b.line_count && a.byte_count == b.byte_count && a.token_count == b.token_count
451
+ }