claude-mpm 4.24.0__py3-none-any.whl → 5.0.9__py3-none-any.whl

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.

Potentially problematic release.


This version of claude-mpm might be problematic. Click here for more details.

Files changed (502) hide show
  1. claude_mpm/VERSION +1 -1
  2. claude_mpm/agents/BASE_PM.md +12 -0
  3. claude_mpm/agents/OUTPUT_STYLE.md +3 -48
  4. claude_mpm/agents/PM_INSTRUCTIONS.md +721 -911
  5. claude_mpm/agents/PM_INSTRUCTIONS_TEACH.md +1322 -0
  6. claude_mpm/agents/WORKFLOW.md +4 -4
  7. claude_mpm/agents/__init__.py +6 -0
  8. claude_mpm/agents/agent_loader.py +1 -4
  9. claude_mpm/agents/base_agent.json +6 -3
  10. claude_mpm/agents/base_agent_loader.py +10 -35
  11. claude_mpm/agents/frontmatter_validator.py +1 -1
  12. claude_mpm/agents/templates/{circuit_breakers.md → circuit-breakers.md} +370 -3
  13. claude_mpm/agents/templates/context-management-examples.md +544 -0
  14. claude_mpm/agents/templates/{pm_red_flags.md → pm-red-flags.md} +48 -0
  15. claude_mpm/agents/templates/pr-workflow-examples.md +427 -0
  16. claude_mpm/agents/templates/research-gate-examples.md +669 -0
  17. claude_mpm/agents/templates/structured-questions-examples.md +615 -0
  18. claude_mpm/agents/templates/ticket-completeness-examples.md +139 -0
  19. claude_mpm/agents/templates/ticketing-examples.md +277 -0
  20. claude_mpm/cli/__init__.py +38 -2
  21. claude_mpm/cli/commands/__init__.py +2 -0
  22. claude_mpm/cli/commands/agent_source.py +774 -0
  23. claude_mpm/cli/commands/agent_state_manager.py +188 -30
  24. claude_mpm/cli/commands/agents.py +959 -36
  25. claude_mpm/cli/commands/agents_cleanup.py +210 -0
  26. claude_mpm/cli/commands/agents_discover.py +338 -0
  27. claude_mpm/cli/commands/aggregate.py +1 -1
  28. claude_mpm/cli/commands/analyze.py +3 -3
  29. claude_mpm/cli/commands/auto_configure.py +2 -6
  30. claude_mpm/cli/commands/config.py +7 -4
  31. claude_mpm/cli/commands/configure.py +769 -45
  32. claude_mpm/cli/commands/configure_agent_display.py +4 -4
  33. claude_mpm/cli/commands/configure_navigation.py +63 -46
  34. claude_mpm/cli/commands/debug.py +12 -12
  35. claude_mpm/cli/commands/doctor.py +10 -2
  36. claude_mpm/cli/commands/hook_errors.py +277 -0
  37. claude_mpm/cli/commands/local_deploy.py +1 -4
  38. claude_mpm/cli/commands/mcp_install_commands.py +1 -1
  39. claude_mpm/cli/commands/mpm_init/core.py +49 -1
  40. claude_mpm/cli/commands/mpm_init/git_activity.py +10 -10
  41. claude_mpm/cli/commands/mpm_init/prompts.py +6 -6
  42. claude_mpm/cli/commands/postmortem.py +401 -0
  43. claude_mpm/cli/commands/run.py +123 -165
  44. claude_mpm/cli/commands/skill_source.py +694 -0
  45. claude_mpm/cli/commands/skills.py +757 -20
  46. claude_mpm/cli/executor.py +78 -3
  47. claude_mpm/cli/interactive/agent_wizard.py +955 -45
  48. claude_mpm/cli/parsers/agent_source_parser.py +171 -0
  49. claude_mpm/cli/parsers/agents_parser.py +256 -4
  50. claude_mpm/cli/parsers/base_parser.py +53 -0
  51. claude_mpm/cli/parsers/config_parser.py +96 -43
  52. claude_mpm/cli/parsers/skill_source_parser.py +169 -0
  53. claude_mpm/cli/parsers/skills_parser.py +145 -0
  54. claude_mpm/cli/parsers/source_parser.py +138 -0
  55. claude_mpm/cli/startup.py +538 -106
  56. claude_mpm/cli/startup_display.py +480 -0
  57. claude_mpm/cli/utils.py +1 -1
  58. claude_mpm/cli_module/commands.py +1 -1
  59. claude_mpm/commands/{mpm-auto-configure.md → mpm-agents-auto-configure.md} +9 -0
  60. claude_mpm/commands/mpm-agents-detect.md +9 -0
  61. claude_mpm/commands/{mpm-agents.md → mpm-agents-list.md} +9 -0
  62. claude_mpm/commands/mpm-agents-recommend.md +9 -0
  63. claude_mpm/commands/{mpm-config.md → mpm-config-view.md} +9 -0
  64. claude_mpm/commands/mpm-doctor.md +9 -0
  65. claude_mpm/commands/mpm-help.md +14 -2
  66. claude_mpm/commands/mpm-init.md +27 -2
  67. claude_mpm/commands/mpm-monitor.md +9 -0
  68. claude_mpm/commands/mpm-postmortem.md +123 -0
  69. claude_mpm/commands/{mpm-resume.md → mpm-session-resume.md} +9 -0
  70. claude_mpm/commands/mpm-status.md +9 -0
  71. claude_mpm/commands/{mpm-organize.md → mpm-ticket-organize.md} +9 -0
  72. claude_mpm/commands/mpm-ticket-view.md +552 -0
  73. claude_mpm/commands/mpm-version.md +9 -0
  74. claude_mpm/commands/mpm.md +10 -0
  75. claude_mpm/config/agent_presets.py +488 -0
  76. claude_mpm/config/agent_sources.py +325 -0
  77. claude_mpm/config/skill_presets.py +392 -0
  78. claude_mpm/config/skill_sources.py +590 -0
  79. claude_mpm/constants.py +13 -0
  80. claude_mpm/core/claude_runner.py +5 -34
  81. claude_mpm/core/config.py +16 -0
  82. claude_mpm/core/constants.py +1 -1
  83. claude_mpm/core/framework/__init__.py +3 -16
  84. claude_mpm/core/framework/loaders/file_loader.py +54 -101
  85. claude_mpm/core/framework/loaders/instruction_loader.py +25 -5
  86. claude_mpm/core/hook_error_memory.py +381 -0
  87. claude_mpm/core/hook_manager.py +41 -2
  88. claude_mpm/core/interactive_session.py +91 -10
  89. claude_mpm/core/logger.py +3 -1
  90. claude_mpm/core/oneshot_session.py +71 -8
  91. claude_mpm/core/protocols/__init__.py +23 -0
  92. claude_mpm/core/protocols/runner_protocol.py +103 -0
  93. claude_mpm/core/protocols/session_protocol.py +131 -0
  94. claude_mpm/core/shared/singleton_manager.py +11 -4
  95. claude_mpm/core/system_context.py +38 -0
  96. claude_mpm/dashboard/static/css/activity.css +69 -69
  97. claude_mpm/dashboard/static/css/connection-status.css +10 -10
  98. claude_mpm/dashboard/static/css/dashboard.css +15 -15
  99. claude_mpm/dashboard/static/js/components/activity-tree.js +178 -178
  100. claude_mpm/dashboard/static/js/components/agent-hierarchy.js +101 -101
  101. claude_mpm/dashboard/static/js/components/agent-inference.js +31 -31
  102. claude_mpm/dashboard/static/js/components/build-tracker.js +59 -59
  103. claude_mpm/dashboard/static/js/components/code-simple.js +107 -107
  104. claude_mpm/dashboard/static/js/components/connection-debug.js +101 -101
  105. claude_mpm/dashboard/static/js/components/diff-viewer.js +113 -113
  106. claude_mpm/dashboard/static/js/components/event-viewer.js +12 -12
  107. claude_mpm/dashboard/static/js/components/file-change-tracker.js +57 -57
  108. claude_mpm/dashboard/static/js/components/file-change-viewer.js +74 -74
  109. claude_mpm/dashboard/static/js/components/file-tool-tracker.js +6 -6
  110. claude_mpm/dashboard/static/js/components/file-viewer.js +42 -42
  111. claude_mpm/dashboard/static/js/components/module-viewer.js +27 -27
  112. claude_mpm/dashboard/static/js/components/session-manager.js +14 -14
  113. claude_mpm/dashboard/static/js/components/socket-manager.js +1 -1
  114. claude_mpm/dashboard/static/js/components/ui-state-manager.js +14 -14
  115. claude_mpm/dashboard/static/js/components/unified-data-viewer.js +110 -110
  116. claude_mpm/dashboard/static/js/components/working-directory.js +8 -8
  117. claude_mpm/dashboard/static/js/connection-manager.js +76 -76
  118. claude_mpm/dashboard/static/js/dashboard.js +76 -58
  119. claude_mpm/dashboard/static/js/extension-error-handler.js +22 -22
  120. claude_mpm/dashboard/static/js/socket-client.js +138 -121
  121. claude_mpm/dashboard/templates/code_simple.html +23 -23
  122. claude_mpm/dashboard/templates/index.html +18 -18
  123. claude_mpm/experimental/cli_enhancements.py +1 -5
  124. claude_mpm/hooks/claude_hooks/__pycache__/__init__.cpython-313.pyc +0 -0
  125. claude_mpm/hooks/claude_hooks/__pycache__/event_handlers.cpython-313.pyc +0 -0
  126. claude_mpm/hooks/claude_hooks/__pycache__/hook_handler.cpython-313.pyc +0 -0
  127. claude_mpm/hooks/claude_hooks/__pycache__/memory_integration.cpython-313.pyc +0 -0
  128. claude_mpm/hooks/claude_hooks/__pycache__/response_tracking.cpython-313.pyc +0 -0
  129. claude_mpm/hooks/claude_hooks/__pycache__/tool_analysis.cpython-313.pyc +0 -0
  130. claude_mpm/hooks/claude_hooks/event_handlers.py +3 -1
  131. claude_mpm/hooks/claude_hooks/services/__pycache__/__init__.cpython-313.pyc +0 -0
  132. claude_mpm/hooks/claude_hooks/services/__pycache__/connection_manager_http.cpython-313.pyc +0 -0
  133. claude_mpm/hooks/claude_hooks/services/__pycache__/duplicate_detector.cpython-313.pyc +0 -0
  134. claude_mpm/hooks/claude_hooks/services/__pycache__/state_manager.cpython-313.pyc +0 -0
  135. claude_mpm/hooks/claude_hooks/services/__pycache__/subagent_processor.cpython-313.pyc +0 -0
  136. claude_mpm/hooks/failure_learning/__init__.py +2 -8
  137. claude_mpm/hooks/failure_learning/failure_detection_hook.py +1 -6
  138. claude_mpm/hooks/failure_learning/fix_detection_hook.py +1 -6
  139. claude_mpm/hooks/failure_learning/learning_extraction_hook.py +1 -6
  140. claude_mpm/hooks/kuzu_response_hook.py +1 -5
  141. claude_mpm/models/git_repository.py +198 -0
  142. claude_mpm/scripts/claude-hook-handler.sh +3 -3
  143. claude_mpm/scripts/start_activity_logging.py +3 -1
  144. claude_mpm/services/agents/agent_builder.py +45 -9
  145. claude_mpm/services/agents/agent_preset_service.py +238 -0
  146. claude_mpm/services/agents/agent_selection_service.py +484 -0
  147. claude_mpm/services/agents/auto_deploy_index_parser.py +569 -0
  148. claude_mpm/services/agents/cache_git_manager.py +621 -0
  149. claude_mpm/services/agents/deployment/agent_deployment.py +126 -2
  150. claude_mpm/services/agents/deployment/agent_discovery_service.py +105 -73
  151. claude_mpm/services/agents/deployment/agent_format_converter.py +1 -1
  152. claude_mpm/services/agents/deployment/agent_lifecycle_manager.py +1 -5
  153. claude_mpm/services/agents/deployment/agent_metrics_collector.py +3 -3
  154. claude_mpm/services/agents/deployment/agent_restore_handler.py +1 -4
  155. claude_mpm/services/agents/deployment/agent_template_builder.py +236 -15
  156. claude_mpm/services/agents/deployment/agents_directory_resolver.py +101 -15
  157. claude_mpm/services/agents/deployment/async_agent_deployment.py +2 -1
  158. claude_mpm/services/agents/deployment/facade/deployment_facade.py +3 -3
  159. claude_mpm/services/agents/deployment/multi_source_deployment_service.py +115 -15
  160. claude_mpm/services/agents/deployment/pipeline/pipeline_executor.py +2 -2
  161. claude_mpm/services/agents/deployment/refactored_agent_deployment_service.py +1 -4
  162. claude_mpm/services/agents/deployment/remote_agent_discovery_service.py +363 -0
  163. claude_mpm/services/agents/deployment/single_agent_deployer.py +2 -2
  164. claude_mpm/services/agents/deployment/system_instructions_deployer.py +168 -46
  165. claude_mpm/services/agents/deployment/validation/deployment_validator.py +2 -2
  166. claude_mpm/services/agents/git_source_manager.py +629 -0
  167. claude_mpm/services/agents/loading/framework_agent_loader.py +9 -12
  168. claude_mpm/services/agents/local_template_manager.py +50 -10
  169. claude_mpm/services/agents/single_tier_deployment_service.py +696 -0
  170. claude_mpm/services/agents/sources/__init__.py +13 -0
  171. claude_mpm/services/agents/sources/agent_sync_state.py +516 -0
  172. claude_mpm/services/agents/sources/git_source_sync_service.py +1087 -0
  173. claude_mpm/services/agents/startup_sync.py +239 -0
  174. claude_mpm/services/agents/toolchain_detector.py +474 -0
  175. claude_mpm/services/analysis/__init__.py +25 -0
  176. claude_mpm/services/analysis/postmortem_reporter.py +474 -0
  177. claude_mpm/services/analysis/postmortem_service.py +765 -0
  178. claude_mpm/services/cli/session_pause_manager.py +1 -1
  179. claude_mpm/services/command_deployment_service.py +200 -6
  180. claude_mpm/services/core/base.py +7 -2
  181. claude_mpm/services/core/interfaces/__init__.py +1 -3
  182. claude_mpm/services/core/interfaces/health.py +1 -4
  183. claude_mpm/services/core/models/__init__.py +2 -11
  184. claude_mpm/services/diagnostics/checks/__init__.py +4 -0
  185. claude_mpm/services/diagnostics/checks/agent_check.py +0 -2
  186. claude_mpm/services/diagnostics/checks/agent_sources_check.py +577 -0
  187. claude_mpm/services/diagnostics/checks/instructions_check.py +1 -2
  188. claude_mpm/services/diagnostics/checks/mcp_check.py +0 -1
  189. claude_mpm/services/diagnostics/checks/mcp_services_check.py +7 -15
  190. claude_mpm/services/diagnostics/checks/monitor_check.py +0 -1
  191. claude_mpm/services/diagnostics/checks/skill_sources_check.py +587 -0
  192. claude_mpm/services/diagnostics/diagnostic_runner.py +9 -0
  193. claude_mpm/services/diagnostics/doctor_reporter.py +40 -10
  194. claude_mpm/services/event_bus/direct_relay.py +3 -3
  195. claude_mpm/services/events/consumers/logging.py +1 -2
  196. claude_mpm/services/git/__init__.py +21 -0
  197. claude_mpm/services/git/git_operations_service.py +494 -0
  198. claude_mpm/services/github/__init__.py +21 -0
  199. claude_mpm/services/github/github_cli_service.py +397 -0
  200. claude_mpm/services/infrastructure/monitoring/__init__.py +1 -5
  201. claude_mpm/services/infrastructure/monitoring/aggregator.py +1 -6
  202. claude_mpm/services/instructions/__init__.py +9 -0
  203. claude_mpm/services/instructions/instruction_cache_service.py +374 -0
  204. claude_mpm/services/local_ops/__init__.py +3 -13
  205. claude_mpm/services/local_ops/health_checks/__init__.py +1 -3
  206. claude_mpm/services/local_ops/health_manager.py +1 -4
  207. claude_mpm/services/local_ops/resource_monitor.py +1 -1
  208. claude_mpm/services/mcp_config_manager.py +75 -145
  209. claude_mpm/services/mcp_gateway/config/configuration.py +1 -1
  210. claude_mpm/services/mcp_gateway/core/process_pool.py +22 -16
  211. claude_mpm/services/mcp_gateway/server/mcp_gateway.py +1 -6
  212. claude_mpm/services/mcp_gateway/server/stdio_server.py +0 -2
  213. claude_mpm/services/mcp_gateway/tools/kuzu_memory_service.py +6 -2
  214. claude_mpm/services/mcp_service_verifier.py +6 -3
  215. claude_mpm/services/model/model_router.py +1 -2
  216. claude_mpm/services/monitor/daemon.py +29 -9
  217. claude_mpm/services/monitor/daemon_manager.py +96 -19
  218. claude_mpm/services/monitor/server.py +2 -2
  219. claude_mpm/services/port_manager.py +1 -1
  220. claude_mpm/services/pr/__init__.py +14 -0
  221. claude_mpm/services/pr/pr_template_service.py +329 -0
  222. claude_mpm/services/project/documentation_manager.py +2 -1
  223. claude_mpm/services/project/toolchain_analyzer.py +3 -1
  224. claude_mpm/services/runner_configuration_service.py +16 -3
  225. claude_mpm/services/session_management_service.py +16 -4
  226. claude_mpm/services/skills/__init__.py +18 -0
  227. claude_mpm/services/skills/git_skill_source_manager.py +1169 -0
  228. claude_mpm/services/skills/skill_discovery_service.py +568 -0
  229. claude_mpm/services/skills_config.py +547 -0
  230. claude_mpm/services/skills_deployer.py +955 -0
  231. claude_mpm/services/socketio/handlers/connection.py +1 -1
  232. claude_mpm/services/socketio/handlers/git.py +1 -1
  233. claude_mpm/services/socketio/server/core.py +1 -4
  234. claude_mpm/services/socketio/server/main.py +1 -3
  235. claude_mpm/services/system_instructions_service.py +1 -3
  236. claude_mpm/services/unified/analyzer_strategies/performance_analyzer.py +0 -3
  237. claude_mpm/services/unified/analyzer_strategies/security_analyzer.py +0 -1
  238. claude_mpm/services/unified/deployment_strategies/vercel.py +1 -5
  239. claude_mpm/services/unified/unified_deployment.py +1 -5
  240. claude_mpm/services/version_control/conflict_resolution.py +6 -4
  241. claude_mpm/services/visualization/__init__.py +1 -5
  242. claude_mpm/services/visualization/mermaid_generator.py +2 -3
  243. claude_mpm/skills/bundled/testing/webapp-testing/scripts/with_server.py +2 -2
  244. claude_mpm/skills/skills_registry.py +0 -1
  245. claude_mpm/templates/questions/__init__.py +38 -0
  246. claude_mpm/templates/questions/base.py +193 -0
  247. claude_mpm/templates/questions/pr_strategy.py +311 -0
  248. claude_mpm/templates/questions/project_init.py +385 -0
  249. claude_mpm/templates/questions/ticket_mgmt.py +394 -0
  250. claude_mpm/tools/__main__.py +8 -8
  251. claude_mpm/utils/agent_dependency_loader.py +77 -10
  252. claude_mpm/utils/agent_filters.py +288 -0
  253. claude_mpm/utils/dependency_cache.py +3 -1
  254. claude_mpm/utils/gitignore.py +241 -0
  255. claude_mpm/utils/migration.py +372 -0
  256. claude_mpm/utils/progress.py +387 -0
  257. claude_mpm/utils/robust_installer.py +2 -4
  258. claude_mpm/utils/structured_questions.py +619 -0
  259. {claude_mpm-4.24.0.dist-info → claude_mpm-5.0.9.dist-info}/METADATA +396 -43
  260. {claude_mpm-4.24.0.dist-info → claude_mpm-5.0.9.dist-info}/RECORD +268 -422
  261. claude_mpm/agents/templates/.claude-mpm/memories/README.md +0 -17
  262. claude_mpm/agents/templates/.claude-mpm/memories/engineer_memories.md +0 -3
  263. claude_mpm/agents/templates/agent-manager.json +0 -273
  264. claude_mpm/agents/templates/agentic-coder-optimizer.json +0 -248
  265. claude_mpm/agents/templates/api_qa.json +0 -183
  266. claude_mpm/agents/templates/clerk-ops.json +0 -235
  267. claude_mpm/agents/templates/code_analyzer.json +0 -101
  268. claude_mpm/agents/templates/content-agent.json +0 -358
  269. claude_mpm/agents/templates/dart_engineer.json +0 -307
  270. claude_mpm/agents/templates/data_engineer.json +0 -225
  271. claude_mpm/agents/templates/documentation.json +0 -238
  272. claude_mpm/agents/templates/engineer.json +0 -210
  273. claude_mpm/agents/templates/gcp_ops_agent.json +0 -253
  274. claude_mpm/agents/templates/golang_engineer.json +0 -270
  275. claude_mpm/agents/templates/imagemagick.json +0 -264
  276. claude_mpm/agents/templates/java_engineer.json +0 -346
  277. claude_mpm/agents/templates/javascript_engineer_agent.json +0 -380
  278. claude_mpm/agents/templates/local_ops_agent.json +0 -1840
  279. claude_mpm/agents/templates/logs/prompts/agent_engineer_20250826_014258_728.md +0 -39
  280. claude_mpm/agents/templates/logs/prompts/agent_engineer_20250901_010124_142.md +0 -400
  281. claude_mpm/agents/templates/memory_manager.json +0 -158
  282. claude_mpm/agents/templates/nextjs_engineer.json +0 -285
  283. claude_mpm/agents/templates/ops.json +0 -185
  284. claude_mpm/agents/templates/php-engineer.json +0 -287
  285. claude_mpm/agents/templates/product_owner.json +0 -338
  286. claude_mpm/agents/templates/project_organizer.json +0 -144
  287. claude_mpm/agents/templates/prompt-engineer.json +0 -737
  288. claude_mpm/agents/templates/python_engineer.json +0 -387
  289. claude_mpm/agents/templates/qa.json +0 -243
  290. claude_mpm/agents/templates/react_engineer.json +0 -239
  291. claude_mpm/agents/templates/refactoring_engineer.json +0 -276
  292. claude_mpm/agents/templates/research.json +0 -188
  293. claude_mpm/agents/templates/ruby-engineer.json +0 -280
  294. claude_mpm/agents/templates/rust_engineer.json +0 -275
  295. claude_mpm/agents/templates/security.json +0 -202
  296. claude_mpm/agents/templates/svelte-engineer.json +0 -225
  297. claude_mpm/agents/templates/tauri_engineer.json +0 -274
  298. claude_mpm/agents/templates/ticketing.json +0 -178
  299. claude_mpm/agents/templates/typescript_engineer.json +0 -285
  300. claude_mpm/agents/templates/vercel_ops_agent.json +0 -412
  301. claude_mpm/agents/templates/version_control.json +0 -159
  302. claude_mpm/agents/templates/web_qa.json +0 -400
  303. claude_mpm/agents/templates/web_ui.json +0 -189
  304. claude_mpm/commands/mpm-tickets.md +0 -151
  305. claude_mpm/dashboard/.claude-mpm/socketio-instances.json +0 -1
  306. claude_mpm/dashboard/react/components/DataInspector/DataInspector.module.css +0 -188
  307. claude_mpm/dashboard/react/components/EventViewer/EventViewer.module.css +0 -156
  308. claude_mpm/dashboard/react/components/shared/ConnectionStatus.module.css +0 -38
  309. claude_mpm/dashboard/react/components/shared/FilterBar.module.css +0 -92
  310. claude_mpm/dashboard/static/archive/activity_dashboard_fixed.html +0 -248
  311. claude_mpm/dashboard/static/archive/activity_dashboard_test.html +0 -61
  312. claude_mpm/dashboard/static/archive/test_activity_connection.html +0 -179
  313. claude_mpm/dashboard/static/archive/test_claude_tree_tab.html +0 -68
  314. claude_mpm/dashboard/static/archive/test_dashboard.html +0 -409
  315. claude_mpm/dashboard/static/archive/test_dashboard_fixed.html +0 -519
  316. claude_mpm/dashboard/static/archive/test_dashboard_verification.html +0 -181
  317. claude_mpm/dashboard/static/archive/test_file_data.html +0 -315
  318. claude_mpm/dashboard/static/archive/test_file_tree_empty_state.html +0 -243
  319. claude_mpm/dashboard/static/archive/test_file_tree_fix.html +0 -234
  320. claude_mpm/dashboard/static/archive/test_file_tree_rename.html +0 -117
  321. claude_mpm/dashboard/static/archive/test_file_tree_tab.html +0 -115
  322. claude_mpm/dashboard/static/archive/test_file_viewer.html +0 -224
  323. claude_mpm/dashboard/static/archive/test_final_activity.html +0 -220
  324. claude_mpm/dashboard/static/archive/test_tab_fix.html +0 -139
  325. claude_mpm/dashboard/static/built/assets/events.DjpNxWNo.css +0 -1
  326. claude_mpm/dashboard/static/built/components/activity-tree.js +0 -2
  327. claude_mpm/dashboard/static/built/components/agent-hierarchy.js +0 -777
  328. claude_mpm/dashboard/static/built/components/agent-inference.js +0 -2
  329. claude_mpm/dashboard/static/built/components/build-tracker.js +0 -333
  330. claude_mpm/dashboard/static/built/components/code-simple.js +0 -857
  331. claude_mpm/dashboard/static/built/components/code-tree/tree-breadcrumb.js +0 -353
  332. claude_mpm/dashboard/static/built/components/code-tree/tree-constants.js +0 -235
  333. claude_mpm/dashboard/static/built/components/code-tree/tree-search.js +0 -409
  334. claude_mpm/dashboard/static/built/components/code-tree/tree-utils.js +0 -435
  335. claude_mpm/dashboard/static/built/components/code-tree.js +0 -2
  336. claude_mpm/dashboard/static/built/components/code-viewer.js +0 -2
  337. claude_mpm/dashboard/static/built/components/connection-debug.js +0 -654
  338. claude_mpm/dashboard/static/built/components/diff-viewer.js +0 -891
  339. claude_mpm/dashboard/static/built/components/event-processor.js +0 -2
  340. claude_mpm/dashboard/static/built/components/event-viewer.js +0 -2
  341. claude_mpm/dashboard/static/built/components/export-manager.js +0 -2
  342. claude_mpm/dashboard/static/built/components/file-change-tracker.js +0 -443
  343. claude_mpm/dashboard/static/built/components/file-change-viewer.js +0 -690
  344. claude_mpm/dashboard/static/built/components/file-tool-tracker.js +0 -2
  345. claude_mpm/dashboard/static/built/components/file-viewer.js +0 -2
  346. claude_mpm/dashboard/static/built/components/hud-library-loader.js +0 -2
  347. claude_mpm/dashboard/static/built/components/hud-manager.js +0 -2
  348. claude_mpm/dashboard/static/built/components/hud-visualizer.js +0 -2
  349. claude_mpm/dashboard/static/built/components/module-viewer.js +0 -2
  350. claude_mpm/dashboard/static/built/components/nav-bar.js +0 -145
  351. claude_mpm/dashboard/static/built/components/page-structure.js +0 -429
  352. claude_mpm/dashboard/static/built/components/session-manager.js +0 -2
  353. claude_mpm/dashboard/static/built/components/socket-manager.js +0 -2
  354. claude_mpm/dashboard/static/built/components/ui-state-manager.js +0 -2
  355. claude_mpm/dashboard/static/built/components/unified-data-viewer.js +0 -2
  356. claude_mpm/dashboard/static/built/components/working-directory.js +0 -2
  357. claude_mpm/dashboard/static/built/connection-manager.js +0 -536
  358. claude_mpm/dashboard/static/built/dashboard.js +0 -2
  359. claude_mpm/dashboard/static/built/extension-error-handler.js +0 -164
  360. claude_mpm/dashboard/static/built/react/events.js +0 -30
  361. claude_mpm/dashboard/static/built/shared/dom-helpers.js +0 -396
  362. claude_mpm/dashboard/static/built/shared/event-bus.js +0 -330
  363. claude_mpm/dashboard/static/built/shared/event-filter-service.js +0 -540
  364. claude_mpm/dashboard/static/built/shared/logger.js +0 -385
  365. claude_mpm/dashboard/static/built/shared/page-structure.js +0 -249
  366. claude_mpm/dashboard/static/built/shared/tooltip-service.js +0 -253
  367. claude_mpm/dashboard/static/built/socket-client.js +0 -2
  368. claude_mpm/dashboard/static/built/tab-isolation-fix.js +0 -185
  369. claude_mpm/dashboard/static/dist/assets/events.DjpNxWNo.css +0 -1
  370. claude_mpm/dashboard/static/dist/components/activity-tree.js +0 -2
  371. claude_mpm/dashboard/static/dist/components/agent-inference.js +0 -2
  372. claude_mpm/dashboard/static/dist/components/code-tree.js +0 -2
  373. claude_mpm/dashboard/static/dist/components/code-viewer.js +0 -2
  374. claude_mpm/dashboard/static/dist/components/event-processor.js +0 -2
  375. claude_mpm/dashboard/static/dist/components/event-viewer.js +0 -2
  376. claude_mpm/dashboard/static/dist/components/export-manager.js +0 -2
  377. claude_mpm/dashboard/static/dist/components/file-tool-tracker.js +0 -2
  378. claude_mpm/dashboard/static/dist/components/file-viewer.js +0 -2
  379. claude_mpm/dashboard/static/dist/components/hud-library-loader.js +0 -2
  380. claude_mpm/dashboard/static/dist/components/hud-manager.js +0 -2
  381. claude_mpm/dashboard/static/dist/components/hud-visualizer.js +0 -2
  382. claude_mpm/dashboard/static/dist/components/module-viewer.js +0 -2
  383. claude_mpm/dashboard/static/dist/components/session-manager.js +0 -2
  384. claude_mpm/dashboard/static/dist/components/socket-manager.js +0 -2
  385. claude_mpm/dashboard/static/dist/components/ui-state-manager.js +0 -2
  386. claude_mpm/dashboard/static/dist/components/unified-data-viewer.js +0 -2
  387. claude_mpm/dashboard/static/dist/components/working-directory.js +0 -2
  388. claude_mpm/dashboard/static/dist/dashboard.js +0 -2
  389. claude_mpm/dashboard/static/dist/react/events.js +0 -30
  390. claude_mpm/dashboard/static/dist/socket-client.js +0 -2
  391. claude_mpm/dashboard/static/events.html +0 -607
  392. claude_mpm/dashboard/static/index.html +0 -635
  393. claude_mpm/dashboard/static/js/shared/dom-helpers.js +0 -396
  394. claude_mpm/dashboard/static/js/shared/event-bus.js +0 -330
  395. claude_mpm/dashboard/static/js/shared/logger.js +0 -385
  396. claude_mpm/dashboard/static/js/shared/tooltip-service.js +0 -253
  397. claude_mpm/dashboard/static/js/stores/dashboard-store.js +0 -562
  398. claude_mpm/dashboard/static/legacy/activity.html +0 -736
  399. claude_mpm/dashboard/static/legacy/agents.html +0 -786
  400. claude_mpm/dashboard/static/legacy/files.html +0 -747
  401. claude_mpm/dashboard/static/legacy/tools.html +0 -831
  402. claude_mpm/dashboard/static/monitors.html +0 -431
  403. claude_mpm/dashboard/static/production/events.html +0 -659
  404. claude_mpm/dashboard/static/production/main.html +0 -698
  405. claude_mpm/dashboard/static/production/monitors.html +0 -483
  406. claude_mpm/dashboard/static/test-archive/dashboard.html +0 -635
  407. claude_mpm/dashboard/static/test-archive/debug-events.html +0 -147
  408. claude_mpm/dashboard/static/test-archive/test-navigation.html +0 -256
  409. claude_mpm/dashboard/static/test-archive/test-react-exports.html +0 -180
  410. claude_mpm/dashboard/static/test-archive/test_debug.html +0 -25
  411. claude_mpm/skills/bundled/collaboration/brainstorming/SKILL.md +0 -79
  412. claude_mpm/skills/bundled/collaboration/dispatching-parallel-agents/SKILL.md +0 -178
  413. claude_mpm/skills/bundled/collaboration/dispatching-parallel-agents/references/agent-prompts.md +0 -577
  414. claude_mpm/skills/bundled/collaboration/dispatching-parallel-agents/references/coordination-patterns.md +0 -467
  415. claude_mpm/skills/bundled/collaboration/dispatching-parallel-agents/references/examples.md +0 -537
  416. claude_mpm/skills/bundled/collaboration/dispatching-parallel-agents/references/troubleshooting.md +0 -730
  417. claude_mpm/skills/bundled/collaboration/requesting-code-review/SKILL.md +0 -112
  418. claude_mpm/skills/bundled/collaboration/requesting-code-review/references/code-reviewer-template.md +0 -146
  419. claude_mpm/skills/bundled/collaboration/requesting-code-review/references/review-examples.md +0 -412
  420. claude_mpm/skills/bundled/collaboration/writing-plans/SKILL.md +0 -81
  421. claude_mpm/skills/bundled/collaboration/writing-plans/references/best-practices.md +0 -362
  422. claude_mpm/skills/bundled/collaboration/writing-plans/references/plan-structure-templates.md +0 -312
  423. claude_mpm/skills/bundled/debugging/root-cause-tracing/SKILL.md +0 -152
  424. claude_mpm/skills/bundled/debugging/root-cause-tracing/references/advanced-techniques.md +0 -668
  425. claude_mpm/skills/bundled/debugging/root-cause-tracing/references/examples.md +0 -587
  426. claude_mpm/skills/bundled/debugging/root-cause-tracing/references/integration.md +0 -438
  427. claude_mpm/skills/bundled/debugging/root-cause-tracing/references/tracing-techniques.md +0 -391
  428. claude_mpm/skills/bundled/debugging/systematic-debugging/CREATION-LOG.md +0 -119
  429. claude_mpm/skills/bundled/debugging/systematic-debugging/SKILL.md +0 -148
  430. claude_mpm/skills/bundled/debugging/systematic-debugging/references/anti-patterns.md +0 -483
  431. claude_mpm/skills/bundled/debugging/systematic-debugging/references/examples.md +0 -452
  432. claude_mpm/skills/bundled/debugging/systematic-debugging/references/troubleshooting.md +0 -449
  433. claude_mpm/skills/bundled/debugging/systematic-debugging/references/workflow.md +0 -411
  434. claude_mpm/skills/bundled/debugging/systematic-debugging/test-academic.md +0 -14
  435. claude_mpm/skills/bundled/debugging/systematic-debugging/test-pressure-1.md +0 -58
  436. claude_mpm/skills/bundled/debugging/systematic-debugging/test-pressure-2.md +0 -68
  437. claude_mpm/skills/bundled/debugging/systematic-debugging/test-pressure-3.md +0 -69
  438. claude_mpm/skills/bundled/debugging/verification-before-completion/SKILL.md +0 -131
  439. claude_mpm/skills/bundled/debugging/verification-before-completion/references/gate-function.md +0 -325
  440. claude_mpm/skills/bundled/debugging/verification-before-completion/references/integration-and-workflows.md +0 -490
  441. claude_mpm/skills/bundled/debugging/verification-before-completion/references/red-flags-and-failures.md +0 -425
  442. claude_mpm/skills/bundled/debugging/verification-before-completion/references/verification-patterns.md +0 -499
  443. claude_mpm/skills/bundled/main/artifacts-builder/SKILL.md +0 -86
  444. claude_mpm/skills/bundled/main/internal-comms/SKILL.md +0 -43
  445. claude_mpm/skills/bundled/main/internal-comms/examples/3p-updates.md +0 -47
  446. claude_mpm/skills/bundled/main/internal-comms/examples/company-newsletter.md +0 -65
  447. claude_mpm/skills/bundled/main/internal-comms/examples/faq-answers.md +0 -30
  448. claude_mpm/skills/bundled/main/internal-comms/examples/general-comms.md +0 -16
  449. claude_mpm/skills/bundled/main/mcp-builder/SKILL.md +0 -160
  450. claude_mpm/skills/bundled/main/mcp-builder/reference/design_principles.md +0 -412
  451. claude_mpm/skills/bundled/main/mcp-builder/reference/evaluation.md +0 -602
  452. claude_mpm/skills/bundled/main/mcp-builder/reference/mcp_best_practices.md +0 -915
  453. claude_mpm/skills/bundled/main/mcp-builder/reference/node_mcp_server.md +0 -916
  454. claude_mpm/skills/bundled/main/mcp-builder/reference/python_mcp_server.md +0 -752
  455. claude_mpm/skills/bundled/main/mcp-builder/reference/workflow.md +0 -1237
  456. claude_mpm/skills/bundled/main/skill-creator/SKILL.md +0 -189
  457. claude_mpm/skills/bundled/main/skill-creator/references/best-practices.md +0 -500
  458. claude_mpm/skills/bundled/main/skill-creator/references/creation-workflow.md +0 -464
  459. claude_mpm/skills/bundled/main/skill-creator/references/examples.md +0 -619
  460. claude_mpm/skills/bundled/main/skill-creator/references/progressive-disclosure.md +0 -437
  461. claude_mpm/skills/bundled/main/skill-creator/references/skill-structure.md +0 -231
  462. claude_mpm/skills/bundled/php/espocrm-development/SKILL.md +0 -170
  463. claude_mpm/skills/bundled/php/espocrm-development/references/architecture.md +0 -602
  464. claude_mpm/skills/bundled/php/espocrm-development/references/common-tasks.md +0 -821
  465. claude_mpm/skills/bundled/php/espocrm-development/references/development-workflow.md +0 -742
  466. claude_mpm/skills/bundled/php/espocrm-development/references/frontend-customization.md +0 -726
  467. claude_mpm/skills/bundled/php/espocrm-development/references/hooks-and-services.md +0 -764
  468. claude_mpm/skills/bundled/php/espocrm-development/references/testing-debugging.md +0 -831
  469. claude_mpm/skills/bundled/rust/desktop-applications/SKILL.md +0 -226
  470. claude_mpm/skills/bundled/rust/desktop-applications/references/architecture-patterns.md +0 -901
  471. claude_mpm/skills/bundled/rust/desktop-applications/references/native-gui-frameworks.md +0 -901
  472. claude_mpm/skills/bundled/rust/desktop-applications/references/platform-integration.md +0 -775
  473. claude_mpm/skills/bundled/rust/desktop-applications/references/state-management.md +0 -937
  474. claude_mpm/skills/bundled/rust/desktop-applications/references/tauri-framework.md +0 -770
  475. claude_mpm/skills/bundled/rust/desktop-applications/references/testing-deployment.md +0 -961
  476. claude_mpm/skills/bundled/testing/condition-based-waiting/SKILL.md +0 -119
  477. claude_mpm/skills/bundled/testing/condition-based-waiting/references/patterns-and-implementation.md +0 -253
  478. claude_mpm/skills/bundled/testing/test-driven-development/SKILL.md +0 -145
  479. claude_mpm/skills/bundled/testing/test-driven-development/references/anti-patterns.md +0 -543
  480. claude_mpm/skills/bundled/testing/test-driven-development/references/examples.md +0 -741
  481. claude_mpm/skills/bundled/testing/test-driven-development/references/integration.md +0 -470
  482. claude_mpm/skills/bundled/testing/test-driven-development/references/philosophy.md +0 -458
  483. claude_mpm/skills/bundled/testing/test-driven-development/references/workflow.md +0 -639
  484. claude_mpm/skills/bundled/testing/testing-anti-patterns/SKILL.md +0 -140
  485. claude_mpm/skills/bundled/testing/testing-anti-patterns/references/completeness-anti-patterns.md +0 -572
  486. claude_mpm/skills/bundled/testing/testing-anti-patterns/references/core-anti-patterns.md +0 -411
  487. claude_mpm/skills/bundled/testing/testing-anti-patterns/references/detection-guide.md +0 -569
  488. claude_mpm/skills/bundled/testing/testing-anti-patterns/references/tdd-connection.md +0 -695
  489. claude_mpm/skills/bundled/testing/webapp-testing/SKILL.md +0 -184
  490. claude_mpm/skills/bundled/testing/webapp-testing/decision-tree.md +0 -459
  491. claude_mpm/skills/bundled/testing/webapp-testing/playwright-patterns.md +0 -479
  492. claude_mpm/skills/bundled/testing/webapp-testing/reconnaissance-pattern.md +0 -687
  493. claude_mpm/skills/bundled/testing/webapp-testing/server-management.md +0 -758
  494. claude_mpm/skills/bundled/testing/webapp-testing/troubleshooting.md +0 -868
  495. /claude_mpm/agents/templates/{git_file_tracking.md → git-file-tracking.md} +0 -0
  496. /claude_mpm/agents/templates/{pm_examples.md → pm-examples.md} +0 -0
  497. /claude_mpm/agents/templates/{response_format.md → response-format.md} +0 -0
  498. /claude_mpm/agents/templates/{validation_templates.md → validation-templates.md} +0 -0
  499. {claude_mpm-4.24.0.dist-info → claude_mpm-5.0.9.dist-info}/WHEEL +0 -0
  500. {claude_mpm-4.24.0.dist-info → claude_mpm-5.0.9.dist-info}/entry_points.txt +0 -0
  501. {claude_mpm-4.24.0.dist-info → claude_mpm-5.0.9.dist-info}/licenses/LICENSE +0 -0
  502. {claude_mpm-4.24.0.dist-info → claude_mpm-5.0.9.dist-info}/top_level.txt +0 -0
@@ -1,2 +0,0 @@
1
- window.AgentInference=class{constructor(e){this.eventViewer=e,this.state={currentDelegation:null,sessionAgents:new Map,eventAgentMap:new Map,pmDelegations:new Map,agentToDelegation:new Map,orphanSubagents:new Map,subagentStartEvents:new Map},console.log("Agent inference system initialized")}initialize(){this.state={currentDelegation:null,sessionAgents:new Map,eventAgentMap:new Map,pmDelegations:new Map,agentToDelegation:new Map,orphanSubagents:new Map,subagentStartEvents:new Map}}inferAgentFromEvent(e){const t=e.data||{},n=e.session_id||t.session_id||"unknown",a=e.hook_event_name||t.hook_event_name||e.type||"",s=e.subtype||t.subtype||"",i=e.tool_name||t.tool_name||"";if(Math.random()<.1&&console.log("Agent inference debug:",{eventType:a,toolName:i,hasData:!!e.data,dataKeys:Object.keys(t),eventKeys:Object.keys(e),agentType:e.agent_type||t.agent_type,subagentType:e.subagent_type||t.subagent_type}),"SubagentStop"===a||"subagent_stop"===s){const i=this.extractAgentNameFromEvent(e);return console.log("SubagentStop event detected:",{agentName:i,sessionId:n,eventType:a,subtype:s,rawAgentType:e.agent_type||t.agent_type}),{type:"subagent",confidence:"definitive",agentName:i,reason:"SubagentStop event"}}if("Stop"===a||"stop"===s)return{type:"main_agent",confidence:"definitive",agentName:"PM",reason:"Stop event"};if("Task"===i){const t=this.extractSubagentTypeFromTask(e);if(t)return console.log("Task delegation detected:",{agentName:t,sessionId:n,eventType:a}),{type:"subagent",confidence:"high",agentName:t,reason:"Task tool with subagent_type"}}if("PreToolUse"===a&&"Task"===i){const t=this.extractSubagentTypeFromTask(e);if(t)return{type:"subagent",confidence:"high",agentName:t,reason:"PreToolUse Task delegation"}}{const e=n.toLowerCase();if(["subagent","task","agent-"].some(t=>e.includes(t)))return{type:"subagent",confidence:"medium",agentName:"Subagent",reason:"Session ID pattern"}}const o=e.agent_type||t.agent_type||e.agent_id||t.agent_id,g=e.subagent_type||t.subagent_type;if(g&&"unknown"!==g)return{type:"subagent",confidence:"high",agentName:this.normalizeAgentName(g),reason:"subagent_type field"};if(o&&"unknown"!==o&&"main"!==o)return{type:"subagent",confidence:"medium",agentName:this.normalizeAgentName(o),reason:"agent_type field"};if(t.delegation_details?.agent_type)return{type:"subagent",confidence:"high",agentName:this.normalizeAgentName(t.delegation_details.agent_type),reason:"delegation_details"};if(e.type&&e.type.startsWith("hook.")){const a=e.type.replace("hook.","");if("subagent_start"===a||"SubagentStart"===t.hook_event_name){const e=t.agent_type||t.agent_id||"Subagent";return console.log("SubagentStart event from Socket.IO:",{agentName:e,sessionId:n,hookType:a}),{type:"subagent",confidence:"definitive",agentName:this.normalizeAgentName(e),reason:"Socket.IO hook SubagentStart"}}if("subagent_stop"===a||"SubagentStop"===t.hook_event_name){const e=t.agent_type||t.agent_id||"Subagent";return{type:"subagent",confidence:"high",agentName:this.normalizeAgentName(e),reason:"Socket.IO hook SubagentStop"}}}return{type:"main_agent",confidence:"default",agentName:"PM",reason:"default classification"}}normalizeAgentName(e){if(!e)return"Unknown";const t={engineer:"Engineer Agent",research:"Research Agent",qa:"QA Agent",documentation:"Documentation Agent",security:"Security Agent",ops:"Ops Agent",version_control:"Version Control Agent",data_engineer:"Data Engineer Agent",test_integration:"Test Integration Agent",pm:"PM Agent"}[e.toLowerCase()];if(t)return t;let n=e.replace(/_/g," ").split(" ").map(e=>e.charAt(0).toUpperCase()+e.slice(1).toLowerCase()).join(" ");return n.toLowerCase().includes("agent")||(n+=" Agent"),n}extractSubagentTypeFromTask(e){let t=null;return e.tool_parameters?.subagent_type?t=e.tool_parameters.subagent_type:e.data?.tool_parameters?.subagent_type?t=e.data.tool_parameters.subagent_type:e.data?.delegation_details?.agent_type?t=e.data.delegation_details.agent_type:e.tool_input?.subagent_type&&(t=e.tool_input.subagent_type),t?this.normalizeAgentName(t):null}extractAgentNameFromEvent(e){const t=e.data||{};if("Task"===e.tool_name||"Task"===t.tool_name){const t=this.extractSubagentTypeFromTask(e);if(t)return t}return e.subagent_type&&"unknown"!==e.subagent_type?this.normalizeAgentName(e.subagent_type):t.subagent_type&&"unknown"!==t.subagent_type?this.normalizeAgentName(t.subagent_type):t.delegation_details?.agent_type&&"unknown"!==t.delegation_details.agent_type?this.normalizeAgentName(t.delegation_details.agent_type):e.agent_type&&!["main","unknown"].includes(e.agent_type)?this.normalizeAgentName(e.agent_type):t.agent_type&&!["main","unknown"].includes(t.agent_type)?this.normalizeAgentName(t.agent_type):e.agent_id&&!["main","unknown"].includes(e.agent_id)?this.normalizeAgentName(e.agent_id):t.agent_id&&!["main","unknown"].includes(t.agent_id)?this.normalizeAgentName(t.agent_id):e.agent&&"unknown"!==e.agent?this.normalizeAgentName(e.agent):e.name&&"unknown"!==e.name?this.normalizeAgentName(e.name):"Unknown"}processAgentInference(){const e=this.eventViewer.events;this.state.currentDelegation=null,this.state.sessionAgents.clear(),this.state.eventAgentMap.clear(),this.state.pmDelegations.clear(),this.state.agentToDelegation.clear(),this.state.orphanSubagents.clear(),this.state.subagentStartEvents.clear(),console.log("Processing agent inference for",e.length,"events"),e&&0!==e.length?(e.forEach((e,t)=>{let n;try{const a=this.inferAgentFromEvent(e),s=e.session_id||e.data?.session_id||"default";n=a,this.state.currentDelegation&&"default"===a.confidence&&s===this.state.currentDelegation.sessionId&&(n={type:"subagent",confidence:"inherited",agentName:this.state.currentDelegation.agentName,reason:"inherited from delegation context"});const i=e.hook_event_name||e.data?.hook_event_name||"";if(("SubagentStart"===i||"hook.subagent_start"===e.type||"subagent_start"===e.subtype)&&"subagent"===a.type&&(this.state.subagentStartEvents.has(a.agentName)||this.state.subagentStartEvents.set(a.agentName,[]),this.state.subagentStartEvents.get(a.agentName).push({eventIndex:t,event:e,timestamp:e.timestamp,sessionId:s})),"Task"===e.tool_name&&"subagent"===a.type){const n=`pm_${s}_${t}_${a.agentName}`,i={id:n,agentName:a.agentName,sessionId:s,startIndex:t,endIndex:null,pmCall:e,timestamp:e.timestamp,agentEvents:[]};this.state.pmDelegations.set(n,i),this.state.agentToDelegation.set(a.agentName,n),this.state.currentDelegation={agentName:a.agentName,sessionId:s,startIndex:t,endIndex:null,delegationId:n},console.log("Delegation started:",this.state.currentDelegation)}else if("definitive"===a.confidence&&"SubagentStop event"===a.reason&&this.state.currentDelegation){this.state.currentDelegation.endIndex=t;const e=this.state.pmDelegations.get(this.state.currentDelegation.delegationId);e&&(e.endIndex=t),console.log("Delegation ended:",this.state.currentDelegation),this.state.currentDelegation=null}if(this.state.currentDelegation&&"subagent"===n.type){const a=this.state.pmDelegations.get(this.state.currentDelegation.delegationId);a&&a.agentEvents.push({eventIndex:t,event:e,inference:n})}this.state.eventAgentMap.set(t,n),this.state.sessionAgents.set(s,n),t<5&&console.log(`Event ${t} agent inference:`,{event_type:e.type||e.hook_event_name,subtype:e.subtype,tool_name:e.tool_name,inference:n,hasData:!!e.data,agentType:e.agent_type||e.data?.agent_type})}catch(a){console.error(`Error processing event ${t} for agent inference:`,a),n||(n={type:"main_agent",confidence:"error",agentName:"PM",reason:"error during processing"}),this.state.eventAgentMap.set(t,n)}}),this.identifyOrphanSubagents(e),console.log("Agent inference processing complete. Results:",{total_events:e.length,inferred_agents:this.state.eventAgentMap.size,unique_sessions:this.state.sessionAgents.size,pm_delegations:this.state.pmDelegations.size,agent_to_delegation_mappings:this.state.agentToDelegation.size,orphan_subagents:this.state.orphanSubagents.size})):console.log("No events to process for agent inference")}getInferredAgent(e){return this.state.eventAgentMap.get(e)||null}getInferredAgentForEvent(e){const t=this.eventViewer.events;let n=t.indexOf(e);if(-1===n&&e.timestamp&&(n=t.findIndex(t=>t.timestamp===e.timestamp&&t.session_id===e.session_id)),-1===n)return console.log("Agent inference: Could not find event in events array, performing inline inference"),this.inferAgentFromEvent(e);let a=this.getInferredAgent(n);return a||(a=this.inferAgentFromEvent(e),this.state.eventAgentMap.set(n,a)),a}getCurrentDelegation(){return this.state.currentDelegation}getSessionAgents(){return this.state.sessionAgents}getEventAgentMap(){return this.state.eventAgentMap}getPMDelegations(){return this.state.pmDelegations}getAgentToDelegationMap(){return this.state.agentToDelegation}buildDelegationHierarchy(){const e=this.getPMDelegations(),t=this.eventViewer.events,n={mainPM:{type:"pm",name:"PM",delegations:[],ownEvents:[],totalEvents:0},impliedPM:{type:"pm_implied",name:"Implied PM",delegations:[],ownEvents:[],totalEvents:0}};for(const[s,i]of e)n.mainPM.delegations.push({id:s,agentName:i.agentName,taskContext:this.extractTaskContext(i.pmCall),events:i.agentEvents,startTime:i.timestamp,endTime:i.endIndex?t[i.endIndex]?.timestamp:null,status:i.endIndex?"completed":"active"}),n.mainPM.totalEvents+=i.agentEvents.length;t.forEach((e,t)=>{const a=this.getInferredAgent(t);a&&"main_agent"===a.type&&(n.mainPM.ownEvents.push({eventIndex:t,event:e}),n.mainPM.totalEvents++)});const a=new Map;t.forEach((t,n)=>{const s=this.getInferredAgent(n);if(s&&"subagent"===s.type){let i=!0;for(const[t,a]of e)if(a.agentEvents.some(e=>e.eventIndex===n)){i=!1;break}if(i){const e=s.agentName;a.has(e)||a.set(e,[]),a.get(e).push({eventIndex:n,event:t,inference:s})}}});for(const[s,i]of a)n.impliedPM.delegations.push({id:`implied_${s}`,agentName:s,taskContext:"No explicit PM delegation",events:i,startTime:i[0].event.timestamp,endTime:i[i.length-1].event.timestamp,status:"completed"}),n.impliedPM.totalEvents+=i.length;return n}extractTaskContext(e){if(!e)return"Unknown task";const t=e.tool_parameters||e.data?.tool_parameters||{};return t.task||t.request||t.description||"Task delegation"}identifyOrphanSubagents(e){for(const[t,n]of this.state.subagentStartEvents)for(const a of n){const n=a.eventIndex,s=new Date(a.timestamp).getTime();let i=!1;for(let a=Math.max(0,n-20);a<n;a++){const n=e[a];if(!n)continue;const o=s-new Date(n.timestamp).getTime();if("Task"===n.tool_name&&o>=0&&o<1e4){const e=this.state.eventAgentMap.get(a);if(e&&e.agentName===t){i=!0;break}}}i||this.state.orphanSubagents.set(n,{agentName:t,timestamp:a.timestamp,sessionId:a.sessionId,event:a.event,groupingKey:null})}this.groupOrphanSubagents(5e3)}groupOrphanSubagents(e){const t=Array.from(this.state.orphanSubagents.values()).sort((e,t)=>new Date(e.timestamp)-new Date(t.timestamp));let n=null,a=null;for(const s of t){const t=new Date(s.timestamp).getTime();(!n||a&&t-a>e)&&(n=`implied_pm_${s.sessionId}_${t}`),s.groupingKey=n,a=t}}isOrphanSubagent(e){return this.state.orphanSubagents.has(e)}getOrphanContext(e){return this.state.orphanSubagents.get(e)||null}getOrphanGroups(){const e=new Map;for(const t of this.state.orphanSubagents.values()){const n=t.groupingKey;e.has(n)||e.set(n,[]),e.get(n).push(t)}return e}getUniqueAgentInstances(){const e=new Map;for(const[a,s]of this.state.pmDelegations){const t=s.agentName;e.has(t)||e.set(t,{id:`consolidated_${t}`,type:"consolidated_agent",agentName:t,delegations:[],pmCalls:[],allEvents:[],firstTimestamp:s.timestamp,lastTimestamp:s.timestamp,totalEventCount:s.agentEvents.length,delegationCount:1});const n=e.get(t);n.delegations.push({id:a,pmCall:s.pmCall,timestamp:s.timestamp,eventCount:s.agentEvents.length,startIndex:s.startIndex,endIndex:s.endIndex,events:s.agentEvents}),s.pmCall&&n.pmCalls.push(s.pmCall),n.allEvents=n.allEvents.concat(s.agentEvents),new Date(s.timestamp)<new Date(n.firstTimestamp)&&(n.firstTimestamp=s.timestamp),new Date(s.timestamp)>new Date(n.lastTimestamp)&&(n.lastTimestamp=s.timestamp),n.totalEventCount+=s.agentEvents.length,n.delegationCount++}const t=this.eventViewer.events;for(let a=0;a<t.length;a++){const n=this.getInferredAgent(a);n&&"subagent"===n.type&&!e.has(n.agentName)&&e.set(n.agentName,{id:`consolidated_${n.agentName}`,type:"consolidated_agent",agentName:n.agentName,delegations:[{id:`implied_pm_${n.agentName}_${a}`,pmCall:null,timestamp:t[a].timestamp,eventCount:1,startIndex:a,endIndex:null,events:[{eventIndex:a,event:t[a],inference:n}]}],pmCalls:[],allEvents:[{eventIndex:a,event:t[a],inference:n}],firstTimestamp:t[a].timestamp,lastTimestamp:t[a].timestamp,totalEventCount:1,delegationCount:1,isImplied:!0})}const n=Array.from(e.values()).sort((e,t)=>new Date(e.firstTimestamp)-new Date(t.firstTimestamp));return console.log("Consolidated unique agents:",{total_unique_agents:n.length,agents:n.map(e=>({name:e.agentName,delegations:e.delegationCount,totalEvents:e.totalEventCount}))}),n}};
2
- //# sourceMappingURL=agent-inference.js.map
@@ -1,2 +0,0 @@
1
- class e{constructor(){this.tooltipService=window.tooltipService||null,this.domHelpers=window.domHelpers||null,this.eventBus=window.eventBus||null,this.logger=window.logger?window.logger.createComponentLogger("CodeTree"):console,this.treeUtils=window.treeUtils||null,this.treeConstants=window.treeConstants||{},this.treeSearch=window.treeSearch||null,this.treeBreadcrumb=window.treeBreadcrumb||null,this.container=null,this.svg=null,this.treeData=null,this.root=null,this.treeLayout=null,this.treeGroup=null,this.nodes=new Map,this.stats={files:0,classes:0,functions:0,methods:0,lines:0},this.isRadialLayout=!1,this.margin=this.treeConstants.DEFAULT_MARGIN||{top:20,right:20,bottom:20,left:20},this.width=(this.treeConstants.DEFAULT_WIDTH||960)-this.margin.left-this.margin.right,this.height=(this.treeConstants.DEFAULT_HEIGHT||600)-this.margin.top-this.margin.bottom,this.radius=Math.min(this.width,this.height)/2,this.nodeId=0,this.duration=this.treeConstants.ANIMATION_DURATION||750,this.languageFilter="all",this.searchTerm="",this.tooltip=null,this.initialized=!1,this.analyzing=!1,this.selectedNode=null,this.socket=null,this.autoDiscovered=!1,this.zoom=null,this.structuredDataContent=null,this.selectedASTItem=null,this.activeNode=null,this.loadingNodes=new Set,this.bulkLoadMode=!1,this.expandedPaths=new Set,this.focusedNode=null,this.horizontalNodes=new Set,this.centralSpine=new Set,this.onNodeClick=this.onNodeClick.bind(this),this.showTooltip=this.showTooltip.bind(this),this.hideTooltip=this.hideTooltip.bind(this)}initialize(){if(this.initialized)return;if(this.container=document.getElementById("code-tree-container"),!this.container)return void console.error("Code tree container not found");const e=document.getElementById("code-tab");if(!e)return void console.error("Code tab panel not found");const t=this.getWorkingDirectory();if(!t||"Loading..."===t||"Not selected"===t)return this.showNoWorkingDirectoryMessage(),void(this.initialized=!0);this.setupControls(),this.initializeTreeData(),this.subscribeToEvents(),this.initializeStructuredData();document.getElementById("breadcrumb-content")&&!this.analyzing&&this.updateActivityTicker("Loading project structure...","info"),e.classList.contains("active")&&(this.createVisualization(),this.root&&this.svg&&this.update(this.root),this.autoDiscoverRootLevel()),this.initialized=!0}renderWhenVisible(){const e=this.getWorkingDirectory();e&&"Loading..."!==e&&"Not selected"!==e?(this.removeNoWorkingDirectoryMessage(),this.initialized?(this.svg?this.root&&this.svg&&this.update(this.root):(this.createVisualization(),this.svg&&this.treeGroup&&this.update(this.root)),this.autoDiscovered||this.autoDiscoverRootLevel()):this.initialize()):this.showNoWorkingDirectoryMessage()}setupControls(){const e=document.getElementById("language-filter");e&&e.addEventListener("change",e=>{this.languageFilter=e.target.value,this.filterTree()});const t=document.getElementById("code-search");t&&t.addEventListener("input",e=>{this.searchTerm=e.target.value.toLowerCase(),this.filterTree()});const o=document.getElementById("code-toggle-legend");o&&o.addEventListener("click",()=>this.toggleLegend()),document.addEventListener("workingDirectoryChanged",e=>{this.onWorkingDirectoryChanged(e.detail.directory)})}onWorkingDirectoryChanged(e){if(!e||"Loading..."===e||"Not selected"===e)return this.showNoWorkingDirectoryMessage(),this.autoDiscovered=!1,this.analyzing=!1,this.nodes.clear(),this.loadingNodes.clear(),this.stats={files:0,classes:0,functions:0,methods:0,lines:0},void this.updateStats();this.removeNoWorkingDirectoryMessage(),this.autoDiscovered=!1,this.analyzing=!1,this.nodes.clear(),this.loadingNodes.clear(),this.stats={files:0,classes:0,functions:0,methods:0,lines:0},this.initializeTreeData(),this.svg&&this.update(this.root);const t=document.getElementById("code-tab");t&&t.classList.contains("active")&&this.autoDiscoverRootLevel(),this.updateStats()}showLoading(){let e=document.getElementById("code-tree-loading");if(!e){const t=document.getElementById("code-tree-container");t&&(e=document.createElement("div"),e.id="code-tree-loading",e.innerHTML='\n <div class="code-tree-spinner"></div>\n <div class="code-tree-loading-text">Analyzing code structure...</div>\n ',t.appendChild(e))}e&&e.classList.remove("hidden")}hideLoading(){const e=document.getElementById("code-tree-loading");e&&e.classList.add("hidden")}createVisualization(){if("undefined"==typeof d3)return void console.error("D3.js is not loaded");const e=d3.select("#code-tree-container");if(e.selectAll("*").remove(),this.addTreeControls(),!e||!e.node())return void console.error("Code tree container not found");const t=e.node(),o=t.clientWidth||960,n=t.clientHeight||600;this.width=o-this.margin.left-this.margin.right,this.height=n-this.margin.top-this.margin.bottom,this.radius=Math.min(this.width,this.height)/2,this.svg=e.append("svg").attr("width",o).attr("height",n);const i=o/2,s=n/2;this.isRadialLayout?this.treeGroup=this.svg.append("g").attr("transform",`translate(${i},${s})`):this.treeGroup=this.svg.append("g").attr("transform",`translate(${this.margin.left+100},${s})`),this.isRadialLayout?this.treeLayout=d3.cluster().size([2*Math.PI,this.radius-100]).separation((e,t)=>{if(e.parent==t.parent){const t=Math.max(1,4-e.depth),o=e.parent&&e.parent.children?.length||1,n=o>5?2:o>3?1.5:1,i=1+.2*e.depth;return t*n/(e.depth||1)*i}return 4/(e.depth||1)}):this.treeLayout=d3.tree().nodeSize([30,200]).separation((e,t)=>e.parent==t.parent?1:1.5),this.zoom=d3.zoom().scaleExtent([.1,3]).on("zoom",e=>{this.treeGroup.attr("transform",e.transform),this.adjustTextSizeForZoom(e.transform.k),this.updateZoomLevel(e.transform.k)}),this.svg.call(this.zoom),this.addZoomKeyboardShortcuts(),console.log("[CodeTree] Zoom and pan functionality enabled"),this.addVisualizationControls(),this.tooltip=d3.select("body").append("div").attr("class","code-tree-tooltip").style("opacity",0).style("position","absolute").style("background","rgba(0, 0, 0, 0.8)").style("color","white").style("padding","8px").style("border-radius","4px").style("font-size","12px").style("pointer-events","none")}clearD3Visualization(){this.treeGroup&&(this.treeGroup.selectAll("g.node").remove(),this.treeGroup.selectAll("path.link").remove()),this.nodeId=0}initializeTreeData(){const e=this.getWorkingDirectory();this.treeData={name:"Project Root",path:e||".",type:"root",isDirectory:!0,children:[],loaded:!1,expanded:!0,hasChildren:!0,isRoot:!0},"undefined"!=typeof d3&&(this.root=d3.hierarchy(this.treeData),this.root.x0=this.height/2,this.root.y0=0)}subscribeToEvents(){if(!this.socket)if(window.socket&&window.socket.connected)console.log("[CodeTree] Using existing global socket"),this.socket=window.socket,this.setupEventHandlers();else if(window.dashboard?.socketClient?.socket&&window.dashboard.socketClient.socket.connected)console.log("[CodeTree] Using dashboard socket"),this.socket=window.dashboard.socketClient.socket,this.setupEventHandlers();else if(window.socketClient?.socket&&window.socketClient.socket.connected)console.log("[CodeTree] Using socketClient socket"),this.socket=window.socketClient.socket,this.setupEventHandlers();else if(window.io){console.log("[CodeTree] Creating new socket connection");try{this.socket=io("/"),this.socket.on("connect",()=>{console.log("[CodeTree] Socket connected successfully"),this.setupEventHandlers()}),this.socket.on("disconnect",()=>{console.log("[CodeTree] Socket disconnected")}),this.socket.on("connect_error",e=>{console.error("[CodeTree] Socket connection error:",e)})}catch(e){console.error("[CodeTree] Failed to create socket connection:",e)}}else console.error("[CodeTree] Socket.IO not available - cannot subscribe to events")}autoDiscoverRootLevel(){if(this.autoDiscovered||this.analyzing)return;this.updateActivityTicker("🔍 Discovering project structure...","info");const e=this.getWorkingDirectory();if(!e||"Loading..."===e||"Not selected"===e)return console.warn("Cannot auto-discover: no working directory set"),void this.showNoWorkingDirectoryMessage();if(!e.startsWith("/")&&!e.match(/^[A-Z]:\\/))return console.error("Working directory is not absolute:",e),void this.showNotification("Invalid working directory path","error");this.autoDiscovered=!0,this.analyzing=!0,this.nodes.clear(),this.loadingNodes.clear(),this.stats={files:0,classes:0,functions:0,methods:0,lines:0},this.socket&&!this.socket.hasListeners("code:node:found")&&this.setupEventHandlers(),this.showLoading();const t=e.split("/").pop()||"Project Root";this.updateBreadcrumb(`Discovering structure in ${t}...`,"info"),console.log(`🚀 [ROOT DISCOVERY] Using REST API for root: ${e}`);const o=`${window.location.origin}/api/directory?path=${encodeURIComponent(e)}`;fetch(o).then(e=>{if(!e.ok)throw new Error(`HTTP ${e.status}: ${e.statusText}`);return e.json()}).then(e=>{if(console.log("✅ [ROOT DISCOVERY] REST API response:",e),e.contents&&Array.isArray(e.contents)){this.treeData.children=e.contents.map(e=>({name:e.name,path:e.path,type:e.type||(e.is_directory?"directory":"file"),size:e.size,hasChildren:e.is_directory,children:[],loaded:!1})),this.treeData.loaded=!0,"undefined"!=typeof d3&&(this.root=d3.hierarchy(this.treeData),this.root.x0=this.height/2,this.root.y0=0,this.root.children&&this.root.children.forEach(e=>{e._children=null})),this.svg&&this.update(this.root);const t=e.contents.filter(e=>!e.is_directory).length,o=e.contents.filter(e=>e.is_directory).length;this.stats.files=t,this.updateStats(),this.updateBreadcrumb(`📁 Found ${o} directories and ${t} files`,"success"),this.updateActivityTicker(`📁 Found ${o} directories and ${t} files`,"success"),this.addEventToDisplay(`📁 Loaded ${e.contents.length} items from project root`,"info")}this.analyzing=!1,this.hideLoading()}).catch(t=>{if(console.error("[ROOT DISCOVERY] Error:",t),this.analyzing=!1,this.hideLoading(),this.showNotification(`Failed to load directory: ${t.message}`,"error"),this.socket){console.log("[ROOT DISCOVERY] Falling back to WebSocket");const t={path:e,depth:"top_level",languages:this.getSelectedLanguages(),ignore_patterns:document.getElementById("ignore-patterns")?.value||"",request_id:`discover_${Date.now()}`};this.socket.emit("code:discover:top_level",t)}}),this.updateStats()}analyzeCode(){this.analyzing||this.autoDiscoverRootLevel()}cancelAnalysis(){this.analyzing=!1,this.hideLoading(),this.loadingNodes.clear(),this.socket&&this.socket.emit("code:analysis:cancel")}addTreeControls(){const e=d3.select("#code-tree-container");e.select(".tree-controls-toolbar").remove();const t=e.append("div").attr("class","tree-controls-toolbar");t.append("button").attr("class","tree-control-btn").attr("title","Expand all loaded directories").text("⊞").on("click",()=>this.expandAll()),t.append("button").attr("class","tree-control-btn").attr("title","Collapse all directories").text("⊟").on("click",()=>this.collapseAll()),t.append("button").attr("class","tree-control-btn").attr("id","bulk-load-toggle").attr("title","Toggle bulk loading (load 2 levels at once)").text("↕").on("click",()=>this.toggleBulkLoad()),t.append("button").attr("class","tree-control-btn").attr("title","Toggle between radial and linear layouts").text("◎").on("click",()=>this.toggleLayout()),t.append("button").attr("class","tree-control-btn").attr("title","Zoom in").text("🔍+").on("click",()=>this.zoomIn()),t.append("button").attr("class","tree-control-btn").attr("title","Zoom out").text("🔍-").on("click",()=>this.zoomOut()),t.append("button").attr("class","tree-control-btn").attr("title","Reset zoom to fit tree").text("⌂").on("click",()=>this.resetZoom()),t.append("span").attr("class","zoom-level-display").attr("id","zoom-level-display").text("100%").style("margin-left","8px").style("font-size","11px").style("color","#718096"),t.append("input").attr("class","tree-control-btn").attr("type","text").attr("placeholder","Search...").attr("title","Search for files and directories").style("width","120px").style("text-align","left").on("input",e=>this.searchTree(e.target.value)).on("keydown",e=>{"Escape"===e.key&&(e.target.value="",this.searchTree(""))})}addBreadcrumb(){const e=d3.select("#code-tree-container");e.select(".tree-breadcrumb").remove();e.append("div").attr("class","tree-breadcrumb").append("div").attr("class","breadcrumb-path").attr("id","tree-breadcrumb-path"),this.updateBreadcrumbPath("/")}updateBreadcrumbPath(e){const t=d3.select("#tree-breadcrumb-path");t.selectAll("*").remove();const o=this.getWorkingDirectory();if(!o||"Loading..."===o||"Not selected"===o)return void t.text("No project selected");const n="/"===e?[o.split("/").pop()||"Root"]:e.split("/").filter(e=>e.length>0);n.forEach((e,o)=>{o>0&&t.append("span").attr("class","breadcrumb-separator").text("/"),t.append("span").attr("class",o===n.length-1?"breadcrumb-segment current":"breadcrumb-segment").text(e).on("click",()=>{if(o<n.length-1){const e=n.slice(0,o+1).join("/");this.navigateToPath(e)}})})}expandAll(){if(!this.root)return;const e=t=>{"directory"!==t.data.type&&"root"!==t.data.type&&!t.data.isDirectory||!0!==t.data.loaded||t._children&&(t.children=t._children,t._children=null,t.data.expanded=!0),t.children&&t.children.forEach(e)};e(this.root),this.update(this.root),this.showNotification("Expanded all loaded directories","success")}collapseAll(){if(!this.root)return;const e=t=>{("directory"===t.data.type||"root"===t.data.type||t.data.isDirectory)&&t.children&&(t._children=t.children,t.children=null,t.data.expanded=!1),t._children&&t._children.forEach(e)};e(this.root),this.update(this.root),this.showNotification("Collapsed all directories","info")}toggleBulkLoad(){this.bulkLoadMode=!this.bulkLoadMode;const e=d3.select("#bulk-load-toggle");this.bulkLoadMode?(e.classed("active",!0),this.showNotification("Bulk load enabled - will load 2 levels deep","info")):(e.classed("active",!1),this.showNotification("Bulk load disabled - load 1 level at a time","info"))}navigateToPath(e){this.showNotification(`Navigating to: ${e}`,"info")}searchTree(e){if(!this.root||!this.treeGroup)return;const t=e.toLowerCase().trim();if(this.treeGroup.selectAll(".code-node").classed("search-match",!1),!t)return;const o=[],n=e=>{const i=(e.data.name||"").toLowerCase(),s=(e.data.path||"").toLowerCase();(i.includes(t)||s.includes(t))&&o.push(e),e.children&&e.children.forEach(n),e._children&&e._children.forEach(n)};n(this.root),o.length>0?(this.treeGroup.selectAll(".code-node").data(),o.forEach(e=>{this.treeGroup.selectAll(".code-node").filter(t=>t.data.path===e.data.path).classed("search-match",!0),this.expandPathToNode(e)}),this.showNotification(`Found ${o.length} matches`,"success")):this.showNotification("No matches found","info")}expandPathToNode(e){const t=[];let o=e.parent;for(;o&&o!==this.root;)t.unshift(o),o=o.parent;t.forEach(e=>{"directory"===e.data.type&&e._children&&(e.children=e._children,e._children=null,e.data.expanded=!0)}),t.length>0&&this.update(this.root)}createEventsDisplay(){let e=document.getElementById("analysis-events");if(!e){const t=document.getElementById("code-tree-container");t&&(e=document.createElement("div"),e.id="analysis-events",e.className="analysis-events",e.style.display="none",t.appendChild(e))}}clearEventsDisplay(){const e=document.getElementById("analysis-events");e&&(e.innerHTML="",e.style.display="block")}addEventToDisplay(e,t="info"){const o=document.getElementById("analysis-events");if(o){const n=document.createElement("div");n.className="analysis-event",n.style.borderLeftColor="warning"===t?"#f59e0b":"error"===t?"#ef4444":"#3b82f6";const i=(new Date).toLocaleTimeString();n.innerHTML=`<span style="color: #718096;">[${i}]</span> ${e}`,o.appendChild(n),o.scrollTop=o.scrollHeight}}setupEventHandlers(){this.socket&&(this.socket.on("code:analysis:accepted",e=>this.onAnalysisAccepted(e)),this.socket.on("code:analysis:queued",e=>this.onAnalysisQueued(e)),this.socket.on("code:analysis:start",e=>this.onAnalysisStart(e)),this.socket.on("code:analysis:complete",e=>this.onAnalysisComplete(e)),this.socket.on("code:analysis:cancelled",e=>this.onAnalysisCancelled(e)),this.socket.on("code:analysis:error",e=>this.onAnalysisError(e)),this.socket.on("code:top_level:discovered",e=>this.onTopLevelDiscovered(e)),this.socket.on("code:directory:discovered",e=>this.onDirectoryDiscovered(e)),this.socket.on("code:file:discovered",e=>this.onFileDiscovered(e)),this.socket.on("code:file:analyzed",e=>{console.log("📨 [SOCKET] Received code:file:analyzed event"),this.onFileAnalyzed(e)}),this.socket.on("code:node:found",e=>this.onNodeFound(e)),this.socket.on("code:analysis:progress",e=>this.onProgressUpdate(e)),this.socket.on("code:analysis:error",e=>{console.error("❌ [FILE ANALYSIS] Analysis error:",e),this.showNotification(`Analysis error: ${e.error||"Unknown error"}`,"error")}),this.socket.on("error",e=>{console.error("❌ [SOCKET] Socket error:",e)}),this.socket.on("connect",()=>{console.log("✅ [SOCKET] Connected to server, analysis service should be available"),this.connectionStable=!0}),this.socket.on("disconnect",()=>{console.log("❌ [SOCKET] Disconnected from server - disabling AST analysis"),this.connectionStable=!1,this.analysisTimeouts&&(this.analysisTimeouts.forEach((e,t)=>{clearTimeout(e),this.loadingNodes.delete(t)}),this.analysisTimeouts.clear())}),this.socket.on("code:directory:contents",e=>{if(e.path){let t=e.path;const o=this.getWorkingDirectory();o&&t.startsWith(o)&&(t=t.substring(o.length).replace(/^\//,""),t||(t="."));const n=this.findNodeByPath(t);if(n&&e.children){const o=this.findD3NodeByPath(t);if(o&&this.loadingNodes.has(t)&&(this.removeLoadingPulse(o),this.loadingNodes.delete(t),console.log("🎯 [SUBDIRECTORY LOADING] Successfully completed and removed from loading set:",t)),n.children=e.children.map(e=>{let o;if("."===t||""===t)o=e.name||e.path;else{const n=e.name||e.path;o=`${t}/${n}`}return{...e,path:o,loaded:"directory"!==e.type&&void 0,analyzed:"file"!==e.type&&void 0,expanded:!1,children:[]}}),n.loaded=!0,n.expanded=!0,this.root&&this.svg){const e=this.root;this.root=d3.hierarchy(this.treeData),this.root.x0=this.height/2,this.root.y0=0,this.preserveExpansionState(e,this.root);const o=this.findD3NodeByPath(t);o&&o.children&&o.children.length>0&&(o._children=null,o.data.expanded=!0,console.log("✅ [D3 UPDATE] Node expanded after loading:",t)),this.update(o||this.root)}e.stats&&(this.stats.files+=e.stats.files||0,this.stats.directories+=e.stats.directories||0,this.updateStats()),this.updateBreadcrumb(`Loaded ${e.path}`,"success"),this.hideLoading()}}}),this.socket.on("code:top_level:discovered",e=>{e.items&&Array.isArray(e.items)&&(this.treeData.children=e.items.map(e=>({name:e.name,path:e.path,type:e.type,language:"file"===e.type?this.detectLanguage(e.path):void 0,size:e.size,lines:e.lines,loaded:"directory"!==e.type&&void 0,analyzed:"file"!==e.type&&void 0,expanded:!1,children:[]})),this.treeData.loaded=!0,e.stats&&(this.stats={...this.stats,...e.stats},this.updateStats()),"undefined"!=typeof d3&&(this.clearD3Visualization(),this.root=d3.hierarchy(this.treeData),this.root.x0=this.height/2,this.root.y0=0,this.svg&&this.update(this.root)),this.analyzing=!1,this.hideLoading(),this.updateBreadcrumb(`Discovered ${e.items.length} root items`,"success"),this.showNotification(`Found ${e.items.length} items in project root`,"success"))}))}onAnalysisStart(e){this.analyzing=!0;const t=e.message||"Starting code analysis...";this.updateActivityTicker("🚀 Starting analysis...","info"),this.updateBreadcrumb(t,"info"),this.addEventToDisplay(`🚀 ${t}`,"info"),this.treeData&&0!==this.treeData.children.length||this.initializeTreeData(),this.stats={files:0,classes:0,functions:0,methods:0,lines:0},this.updateStats()}onTopLevelDiscovered(e){this.updateActivityTicker(`📁 Discovered ${(e.items||[]).length} top-level items`,"success"),this.addEventToDisplay(`📁 Found ${(e.items||[]).length} top-level items in project root`,"info");const t=this.getWorkingDirectory(),o=this.findNodeByPath(t);console.log(`🔎 Looking for root node with path "${t}", found:`,o?{name:o.name,path:o.path,currentChildren:o.children?o.children.length:0}:"NOT FOUND"),o&&e.items?(console.log("🌳 Populating root node with children"),o.children=e.items.map(e=>{const t=this.getWorkingDirectory(),o=t?`${t}/${e.name}`.replace(/\/+/g,"/"):e.name;return console.log(` Adding child: ${e.name} with path: ${o}`),{name:e.name,path:o,type:e.type,loaded:"directory"!==e.type&&void 0,analyzed:"file"!==e.type&&void 0,expanded:!1,children:"directory"===e.type?[]:void 0,size:e.size,has_code:e.has_code}}),o.loaded=!0,o.expanded=!0,this.root&&this.svg&&(this.root.data===this.treeData?(console.log("📊 Updating existing D3 tree structure"),this.root.children=o.children.map(e=>{const t=d3.hierarchy(e);return t.parent=this.root,t.depth=1,t}),this.root._children=null,this.root.data.expanded=!0):(console.log("🔄 Recreating D3 tree structure"),this.root=d3.hierarchy(this.treeData),this.root.x0=this.height/2,this.root.y0=0),this.update(this.root)),this.hideLoading(),this.updateBreadcrumb(`Discovered ${e.items.length} items`,"success"),this.showNotification(`Found ${e.items.length} top-level items`,"success")):(console.error("❌ Could not find root node to populate"),this.showNotification("Failed to populate root directory","error")),this.analyzing=!1}onDirectoryDiscovered(e){console.log("🔴 [RAW DATA] Exact data received from backend:",e),console.log("🔴 [RAW DATA] Data type:",typeof e),console.log("🔴 [RAW DATA] Data keys:",Object.keys(e)),console.log("🔴 [RAW DATA] Children field:",e.children),console.log("🔴 [RAW DATA] Children type:",typeof e.children),console.log("🔴 [RAW DATA] Is children array?:",Array.isArray(e.children)),console.log("🔴 [RAW DATA] Children length:",e.children?e.children.length:"undefined"),this.updateActivityTicker(`📁 Discovered: ${e.name||"directory"}`),this.addEventToDisplay(`📁 Found ${(e.children||[]).length} items in: ${e.name||e.path}`,"info"),console.log("✅ [SUBDIRECTORY LOADING] Received directory discovery response:",{path:e.path,name:e.name,childrenCount:(e.children||[]).length,children:(e.children||[]).map(e=>({name:e.name,type:e.type})),workingDir:this.getWorkingDirectory(),fullEventData:e});let t=e.path;const o=this.getWorkingDirectory();o&&t.startsWith(o)&&(t=t.substring(o.length).replace(/^\//,""),t||(t=".")),console.log("🔎 Searching for node with path:",t);const n=this.findNodeByPath(t);if(console.log("🔍 Node search result:",{searchPath:t,nodeFound:!!n,nodeName:n?.name,nodePath:n?.path,nodeChildren:n?.children?.length,dataHasChildren:!!e.children,dataChildrenLength:e.children?.length}),n||(console.warn("Node not found! Logging all paths in tree:"),this.logAllPaths(this.treeData)),n){if(console.log("📦 Node found, checking children:",{nodeFound:!0,dataHasChildren:"children"in e,dataChildrenIsArray:Array.isArray(e.children),dataChildrenLength:e.children?.length,dataChildrenValue:e.children}),e.children){console.log(`📂 Updating node ${n.name} with ${e.children.length} children`),n.children=e.children.map(e=>{let o;if("."===t||""===t)o=e.name||e.path;else{const n=e.name||e.path;o=`${t}/${n}`}return{name:e.name,path:o,type:e.type,loaded:"directory"!==e.type&&void 0,analyzed:"file"!==e.type&&void 0,expanded:!1,children:"directory"===e.type?[]:void 0,size:e.size,has_code:e.has_code}}),n.loaded=!0,n.expanded=!0;const o=this.findD3NodeByPath(t);if(o&&this.loadingNodes.has(t)&&(this.removeLoadingPulse(o),this.loadingNodes.delete(t),console.log("🎯 [SUBDIRECTORY LOADING] Successfully completed and removed from loading set (hierarchy update):",t)),this.root&&this.svg){const e=this.root;this.root=d3.hierarchy(this.treeData),this.root.x0=this.height/2,this.root.y0=0,this.preserveExpansionState(e,this.root);const o=this.findD3NodeByPath(t);o&&(o.children&&o.children.length>0?(o._children=null,o.data.expanded=!0,console.log("✅ [D3 UPDATE] Node expanded with children:",{path:t,d3ChildrenCount:o.children.length,dataChildrenCount:o.data.children?o.data.children.length:0,childPaths:o.children.map(e=>e.data.path)})):!o.children&&o.data.children&&o.data.children.length>0&&console.error("⚠️ [D3 UPDATE] Data has children but D3 node does not!",{path:t,dataChildren:o.data.children})),this.update(o||this.root)}0===n.children.length?(this.updateBreadcrumb(`Empty directory: ${n.name}`,"info"),this.showNotification(`Directory "${n.name}" is empty`,"info")):(this.updateBreadcrumb(`Loaded ${n.children.length} items from ${n.name}`,"success"),this.showNotification(`Loaded ${n.children.length} items from "${n.name}"`,"success"))}else console.error("❌ No children data received for directory:",{path:t,dataKeys:Object.keys(e),fullData:e}),this.updateBreadcrumb(`Error loading ${n.name}`,"error"),this.showNotification("Failed to load directory contents","error");this.updateStats()}else if(n){if(n&&!e.children){console.warn("⚠️ [SUBDIRECTORY LOADING] Directory response has no children:",{path:e.path,searchPath:t,nodeExists:!!n,dataKeys:Object.keys(e),fullData:e});const o=e.path?e.path.split("/").filter(e=>e):[];if(1===o.length||e.forceAdd){const t={name:e.name||o[o.length-1]||"Unknown",path:e.path,type:"directory",children:[],loaded:!1,expanded:!1,stats:e.stats||{}};this.addNodeToTree(t,e.parent||""),this.updateBreadcrumb(`Discovered: ${e.path}`,"info")}}}else console.error("❌ [SUBDIRECTORY LOADING] Node not found for path:",{searchPath:t,originalPath:e.path,workingDir:this.getWorkingDirectory(),allTreePaths:this.getAllTreePaths(this.treeData)}),this.showNotification(`Could not find directory "${t}" in tree`,"error"),this.logAllPaths(this.treeData)}onFileDiscovered(e){const t=e.name||(e.path?e.path.split("/").pop():"file");this.updateActivityTicker(`📄 Found: ${t}`),this.addEventToDisplay(`📄 Discovered: ${e.path||"Unknown file"}`,"info");const o=e.path?e.path.split("/").filter(e=>e):[],n=o.slice(0,-1).join("/"),i={name:e.name||o[o.length-1]||"Unknown",path:e.path,type:"file",language:e.language||this.detectLanguage(e.path),size:e.size||0,lines:e.lines||0,children:[],analyzed:!1};this.addNodeToTree(i,n),this.stats.files++,this.updateStats(),this.updateBreadcrumb(`Found: ${e.path}`,"info")}onFileAnalyzed(e){if(console.log("✅ [FILE ANALYSIS] Received analysis result:",{path:e.path,elements:e.elements?e.elements.length:0,complexity:e.complexity,lines:e.lines,stats:e.stats,elementsDetail:e.elements,fullData:e}),e.elements&&e.elements.length>0){console.log("🔍 [AST ELEMENTS] Found elements:",e.elements.map(e=>({name:e.name,type:e.type,line:e.line,methods:e.methods?e.methods.length:0})));const t=e.path.split("/").pop(),o=this.getElementCounts(e.elements),n=this.formatElementSummary(o);this.showNotification(`${t} - ${n}`,"success"),this.updateBreadcrumb(`${t} - AST parsed: ${n}`,"success")}else{const t=e.path.split("/").pop();console.log("⚠️ [AST ELEMENTS] No elements found in analysis result");const o=this.getFileTypeDescription(t);this.showNotification(`${t} - No structural elements to display in tree`,"info"),this.updateBreadcrumb(`${t} - ${o} analyzed, content not suitable for tree view`,"info")}this.analysisTimeouts&&this.analysisTimeouts.has(e.path)&&(clearTimeout(this.analysisTimeouts.get(e.path)),this.analysisTimeouts.delete(e.path),console.log("⏰ [FILE ANALYSIS] Cleared timeout for:",e.path));const t=this.findD3NodeByPath(e.path);if(t&&this.loadingNodes.has(e.path)&&(this.removeLoadingPulse(t),this.loadingNodes.delete(e.path)),e.path){const t=e.path.split("/").pop();this.updateActivityTicker(`🔍 Analyzed: ${t}`)}const o=this.findNodeByPath(e.path);if(o){if(console.log("🔍 [FILE NODE] Found file node for:",e.path),o.analyzed=!0,o.complexity=e.complexity||0,o.lines=e.lines||0,e.elements&&Array.isArray(e.elements)){const t=e.elements.map(t=>({name:t.name,type:t.type.toLowerCase(),path:`${e.path}#${t.name}`,line:t.line,complexity:t.complexity||1,docstring:t.docstring||"",children:t.methods?t.methods.map(o=>({name:o.name,type:"method",path:`${e.path}#${t.name}.${o.name}`,line:o.line,complexity:o.complexity||1,docstring:o.docstring||""})):[]}));o.children=t,console.log("✅ [FILE NODE] Added children to file node:",{filePath:e.path,childrenCount:t.length,children:t.map(e=>({name:e.name,type:e.type}))}),this.autoExpandFileWithAST(e.path,o)}else console.log("⚠️ [FILE NODE] No elements to add as children");if(e.stats&&(this.stats.classes+=e.stats.classes||0,this.stats.functions+=e.stats.functions||0,this.stats.methods+=e.stats.methods||0,this.stats.lines+=e.stats.lines||0),this.updateStats(),this.root&&o.children&&o.children.length>0){console.log("🔄 [FILE NODE] Recreating D3 hierarchy to include AST children");const t=this.root;this.root=d3.hierarchy(this.treeData),this.root.x0=this.height/2,this.root.y0=0,this.preserveExpansionState(t,this.root);const o=this.findD3NodeByPath(e.path);o&&o.children&&o.children.length>0&&(o._children=null,o.data.expanded=!0,console.log("✅ [FILE NODE] File node expanded to show AST children:",{path:e.path,childrenCount:o.children.length,childNames:o.children.map(e=>e.data.name)})),this.update(this.root)}else this.root&&this.update(this.root);this.updateBreadcrumb(`Analyzed: ${e.path}`,"success")}else console.error("❌ [FILE NODE] Could not find file node for path:",e.path)}onNodeFound(e){const t="class"===e.type?"🏛️":"function"===e.type?"⚡":"method"===e.type?"🔧":"📦";this.addEventToDisplay(`${t} Found ${e.type||"node"}: ${e.name||"Unknown"}`);const o={name:e.name||"Unknown",type:(e.type||"unknown").toLowerCase(),path:e.path||"",line:e.line||0,complexity:e.complexity||1,docstring:e.docstring||""};o.type={class:"class",function:"function",method:"method",module:"module",file:"file",directory:"directory"}[o.type]||o.type;let n="";if(e.parent_path)n=e.parent_path;else if(e.file_path)n=e.file_path;else if(o.path.includes("/")){const e=o.path.split("/");e.pop(),n=e.join("/")}switch(o.type){case"class":this.stats.classes++;break;case"function":this.stats.functions++;break;case"method":this.stats.methods++;break;case"file":this.stats.files++}this.addNodeToTree(o,n),this.updateStats();const i=o.type.charAt(0).toUpperCase()+o.type.slice(1);this.updateBreadcrumb(`Found ${i}: ${o.name}`,"info")}onProgressUpdate(e){const t=e.progress||0,o=e.message||`Processing... ${t}%`;this.updateBreadcrumb(o,"info");const n=document.querySelector(".code-tree-progress");n&&(n.style.width=`${t}%`)}onAnalysisComplete(e){this.analyzing=!1,this.hideLoading(),this.updateActivityTicker("✅ Ready","success"),this.addEventToDisplay("✅ Analysis complete!","success"),this.root&&this.svg&&this.update(this.root),e.stats&&(this.stats={...this.stats,...e.stats},this.updateStats());const t=e.message||`Analysis complete: ${this.stats.files} files, ${this.stats.classes} classes, ${this.stats.functions} functions`;this.updateBreadcrumb(t,"success"),this.showNotification(t,"success")}onAnalysisError(e){this.analyzing=!1,this.hideLoading(),this.loadingNodes.clear();const t=e.message||e.error||"Analysis failed";this.updateBreadcrumb(t,"error"),this.showNotification(t,"error")}onAnalysisAccepted(e){const t=e.message||"Analysis request accepted";this.updateBreadcrumb(t,"info")}onAnalysisQueued(e){const t=`Analysis queued (position ${e.position||0})`;this.updateBreadcrumb(t,"warning"),this.showNotification(t,"info")}onInfoEvent(e){e.type&&e.type.startsWith("discovery.")?"discovery.start"===e.type?this.updateBreadcrumb(e.message,"info"):"discovery.complete"===e.type?(this.updateBreadcrumb(e.message,"success"),e.stats):"discovery.directory"!==e.type&&"discovery.file"!==e.type||this.updateBreadcrumb(e.message,"info"):e.type&&e.type.startsWith("analysis.")?"analysis.start"===e.type?this.updateBreadcrumb(e.message,"info"):"analysis.complete"===e.type?(this.updateBreadcrumb(e.message,"success"),e.stats&&(e.stats.classes,e.stats.functions,e.stats.methods)):("analysis.class"===e.type||"analysis.function"===e.type||"analysis.method"===e.type||"analysis.parse"===e.type)&&this.updateBreadcrumb(e.message,"info"):e.type&&e.type.startsWith("filter.")?(window.debugMode||this.showFilterEvents)&&(console.debug("[FILTER]",e.type,e.path,e.reason),this.showFilterEvents&&this.updateBreadcrumb(e.message,"warning")):e.type&&e.type.startsWith("cache.")&&("cache.hit"===e.type?(console.debug("[CACHE HIT]",e.file),this.showCacheEvents&&this.updateBreadcrumb(e.message,"info")):"cache.miss"===e.type&&console.debug("[CACHE MISS]",e.file)),this.eventLogEnabled&&e.message&&this.addEventToDisplay(e)}addEventToDisplay(e){this.recentEvents||(this.recentEvents=[]),this.recentEvents.unshift({timestamp:e.timestamp||(new Date).toISOString(),type:e.type,message:e.message,data:e}),this.recentEvents.length>100&&this.recentEvents.pop()}onAnalysisCancelled(e){this.analyzing=!1,this.hideLoading(),this.loadingNodes.clear();const t=e.message||"Analysis cancelled";this.updateBreadcrumb(t,"warning")}showNotification(e,t="info"){const o=document.createElement("div");o.className=`code-tree-notification ${t}`,o.textContent=e;const n=document.getElementById("code-tree-container");n&&(o.style.position="absolute",o.style.top="10px",o.style.right="10px",o.style.zIndex="1000",n.style.position&&"static"!==n.style.position||(n.style.position="relative"),n.appendChild(o),setTimeout(()=>{o.style.animation="slideOutRight 0.3s ease",setTimeout(()=>o.remove(),300)},3e3))}addNodeToTree(e,t=""){if(e.path&&e.path.startsWith("/"))return void console.error("Absolute path detected in node, skipping:",e.path);if(t&&t.startsWith("/"))return void console.error("Absolute path detected in parent, skipping:",t);let o=this.treeData;if(t&&(o=this.findNodeByPath(t),!o))return console.warn("Parent node not found, skipping node creation:",t),void console.warn("Attempted to add node:",e);const n=o.children?.find(t=>t.path===e.path||t.name===e.name&&t.type===e.type);n?Object.assign(n,e):(o.children||(o.children=[]),e.children||(e.children=[]),o.children.push(e),this.nodes.set(e.path,e),this.root&&this.svg&&(this.root=d3.hierarchy(this.treeData),this.root.x0=this.height/2,this.root.y0=0,(this.nodes.size<1e3||this.nodes.size%100==0)&&this.update(this.root)))}findNodeByPath(e,t=null){if(t||(t=this.treeData,console.log("🔍 [SUBDIRECTORY LOADING] Starting search for path:",e)),t.path===e)return console.log("✅ [SUBDIRECTORY LOADING] Found node for path:",e),t;if(t.children)for(const o of t.children){const t=this.findNodeByPath(e,o);if(t)return t}return t.parent||t!==this.treeData||console.warn("❌ [SUBDIRECTORY LOADING] Path not found in tree:",e),null}logAllPaths(e,t=""){if(console.log(`${t}${e.path} (${e.name})`),e.children)for(const o of e.children)this.logAllPaths(o,t+" ")}getAllTreePaths(e){const t=[e.path];if(e.children)for(const o of e.children)t.push(...this.getAllTreePaths(o));return t}findD3NodeByPath(e){return this.root?this.root.descendants().find(t=>t.data.path===e):null}preserveExpansionState(e,t){if(!e||!t)return;const o=new Map;e.descendants().forEach(e=>{(e.data.expanded||e.children&&!e._children)&&o.set(e.data.path,!0)}),t.descendants().forEach(e=>{o.has(e.data.path)&&(e.children=e._children||e.children,e._children=null,e.data.expanded=!0)})}updateStats(){const e={"stats-files":this.stats.files,"stats-classes":this.stats.classes,"stats-functions":this.stats.functions,"stats-methods":this.stats.methods};for(const[o,n]of Object.entries(e)){const e=document.getElementById(o);e&&(e.textContent=n.toLocaleString())}const t=document.getElementById("code-progress-text");if(t){const e=this.analyzing?`Analyzing... ${this.stats.files} files processed`:`Ready - ${this.stats.files} files in tree`;t.textContent=e}}updateBreadcrumb(e,t="info"){const o=document.getElementById("breadcrumb-content");o&&(o.textContent=e,o.className=`breadcrumb-${t}`)}async analyzeFileHTTP(e,t,o){console.log("🌐 [HTTP FALLBACK] Analyzing file via HTTP:",e),console.log("🌐 [HTTP FALLBACK] File name:",t);try{const o=this.createMockAnalysisData(e,t);console.log("🌐 [HTTP FALLBACK] Created mock data:",o),setTimeout(()=>{console.log("✅ [HTTP FALLBACK] Mock analysis complete for:",t),console.log("✅ [HTTP FALLBACK] Calling onFileAnalyzed with:",o),this.onFileAnalyzed(o)},1e3)}catch(n){console.error("❌ [HTTP FALLBACK] Analysis failed:",n),this.showNotification(`Analysis failed: ${n.message}`,"error"),this.loadingNodes.delete(e),this.removeLoadingPulse(o)}}createMockAnalysisData(e,t){const o=t.split(".").pop()?.toLowerCase();console.log("🔍 [MOCK DATA] Creating mock data for file:",t,"extension:",o);let n=[];return n="py"===o?[{name:"ExampleClass",type:"class",line:10,complexity:3,docstring:"Example class for demonstration",methods:[{name:"__init__",type:"method",line:12,complexity:1},{name:"example_method",type:"method",line:18,complexity:2}]},{name:"example_function",type:"function",line:25,complexity:2,docstring:"Example function"}]:"js"===o||"ts"===o?[{name:"ExampleClass",type:"class",line:5,complexity:2,methods:[{name:"constructor",type:"method",line:6,complexity:1},{name:"exampleMethod",type:"method",line:10,complexity:2}]},{name:"exampleFunction",type:"function",line:20,complexity:1}]:[{name:"mock_element",type:"function",line:1,complexity:1,docstring:`Mock element for ${t}`}],console.log("🔍 [MOCK DATA] Created elements:",n),{path:e,elements:n,complexity:n.reduce((e,t)=>e+(t.complexity||1),0),lines:50,stats:{classes:n.filter(e=>"class"===e.type).length,functions:n.filter(e=>"function"===e.type).length,methods:n.reduce((e,t)=>e+(t.methods?t.methods.length:0),0),lines:50}}}getSelectedLanguages(){const e=[],t=document.querySelectorAll(".language-checkbox:checked");return console.log("🔍 [LANGUAGE] Found checkboxes:",t.length),console.log("🔍 [LANGUAGE] All language checkboxes:",document.querySelectorAll(".language-checkbox").length),t.forEach(t=>{console.log("🔍 [LANGUAGE] Checked language:",t.value),e.push(t.value)}),0===e.length&&(console.warn("⚠️ [LANGUAGE] No languages selected, using defaults"),e.push("python","javascript","typescript"),document.querySelectorAll(".language-checkbox").forEach(e=>{["python","javascript","typescript"].includes(e.value)&&(e.checked=!0,console.log("✅ [LANGUAGE] Auto-checked:",e.value))})),e}detectLanguage(e){return{py:"python",js:"javascript",ts:"typescript",jsx:"javascript",tsx:"typescript",java:"java",cpp:"cpp",c:"c",cs:"csharp",rb:"ruby",go:"go",rs:"rust",php:"php",swift:"swift",kt:"kotlin",scala:"scala",r:"r",sh:"bash",ps1:"powershell"}[e.split(".").pop().toLowerCase()]||"unknown"}addVisualizationControls(){const e=this.svg.append("g").attr("class","viz-controls").attr("transform","translate(10, 10)").append("g").attr("class","layout-toggle").style("cursor","pointer").on("click",()=>this.toggleLayout());e.append("rect").attr("width",120).attr("height",30).attr("rx",5).attr("fill","#3b82f6").attr("opacity",.8),e.append("text").attr("x",60).attr("y",20).attr("text-anchor","middle").attr("fill","white").style("font-size","12px").text(this.isRadialLayout?"Switch to Linear":"Switch to Radial")}toggleLayout(){this.isRadialLayout=!this.isRadialLayout,this.createVisualization(),this.root&&this.update(this.root),this.showNotification(this.isRadialLayout?"Switched to radial layout":"Switched to linear layout","info")}radialPoint(e,t){return[(t=+t)*Math.cos(e-=Math.PI/2),t*Math.sin(e)]}applySingletonHorizontalLayout(e){this.isRadialLayout||(this.horizontalNodes.clear(),this.centralSpine.clear(),this.identifyCentralSpine(e),this.centralSpine.forEach(e=>{this.horizontalNodes.add(e)}),console.log("🎯 [SPINE] Central spine nodes:",Array.from(this.centralSpine)),console.log("📝 [TEXT] Horizontal text nodes:",Array.from(this.horizontalNodes)))}identifyCentralSpine(e){if(!e||0===e.length)return;const t=e.find(e=>0===e.depth);if(!t)return void console.warn("🎯 [SPINE] No root node found!");this.centralSpine.add(t.data.path),console.log(`🎯 [SPINE] Starting spine with root: ${t.data.name} (${t.data.path})`);let o=t;for(;o&&o.children&&o.children.length>0;){const e=this.selectMainChild(o.children);if(!e)break;this.centralSpine.add(e.data.path),console.log(`🎯 [SPINE] Adding to spine: ${e.data.name}`),o=e}}selectMainChild(e){if(!e||0===e.length)return null;if(1===e.length)return e[0];const t=e.filter(e=>this.isNodeDirectory(e));return 1===t.length||t.length>0?t[0]:e[0]}findSingletonChains(e){const t=[],o=new Set;return e.forEach(e=>{if(!o.has(e)&&e.children&&1===e.children.length){const n=[e];let i=e.children[0];for(console.log(`🔍 [CHAIN] Starting singleton chain with: ${e.data.name} (depth: ${e.depth})`);i&&i.children&&1===i.children.length;)n.push(i),o.add(i),console.log(`🔍 [CHAIN] Adding to chain: ${i.data.name} (depth: ${i.depth})`),i=i.children[0];i&&(n.push(i),o.add(i),console.log(`🔍 [CHAIN] Final node in chain: ${i.data.name} (depth: ${i.depth})`)),n.length>=2?(console.log("✅ [CHAIN] Created horizontal chain:",n.map(e=>e.data.name)),t.push(n),o.add(e)):console.log(`❌ [CHAIN] Chain too short (${n.length}), skipping`)}}),t}layoutChainHorizontally(e){if(e.length<2)return;const t=150,o=e[0],n=o.x,i=o.y;if(2===e.length){const t=i;o.y=t-75,e[1].y=t+75,e[1].x=n}else{const o=i-(e.length-1)*t/2;e.forEach((e,i)=>{e.y=o+i*t,e.x=n})}e.forEach(e=>{this.horizontalNodes.add(e.data.path),console.log(`📝 [TEXT] Marking node for horizontal text: ${e.data.name} (${e.data.path})`)}),console.log(`🔄 [LAYOUT] Horizontal chain of ${e.length} nodes:`,e.map(e=>({name:e.data.name,vertical:e.x,horizontal:e.y}))),console.log("📝 [TEXT] Total horizontal nodes:",Array.from(this.horizontalNodes))}update(e){if(!this.treeLayout||!this.treeGroup||!e)return;const t=this.treeLayout(this.root),o=t.descendants(),n=t.descendants().slice(1);this.applySingletonHorizontalLayout(o),this.isRadialLayout&&o.forEach(e=>{void 0===e.x0&&(e.x0=e.x,e.y0=e.y)});const i=this.treeGroup.selectAll("g.node").data(o,e=>e.id||(e.id=++this.nodeId)),s=i.enter().append("g").attr("class",e=>{let t=["node","code-node"];return this.isNodeDirectory(e)?(t.push("directory"),!0===e.data.loaded&&e.children&&t.push("expanded"),"loading"===e.data.loaded&&t.push("loading"),e.data.children&&0===e.data.children.length&&t.push("empty")):"file"===e.data.type&&t.push("file"),t.join(" ")}).attr("transform",t=>{if(this.isRadialLayout){const[t,o]=this.radialPoint(e.x0||0,e.y0||0);return`translate(${t},${o})`}return`translate(${e.y0},${e.x0})`}).on("click",(e,t)=>{console.log("🔴 [G-ELEMENT] Click on node group element!",{nodeName:t?.data?.name,nodePath:t?.data?.path,eventTarget:e.target.tagName,thisContext:this,hasOnNodeClick:"function"==typeof this.onNodeClick}),this.onNodeClick(e,t)});s.append("circle").attr("class","node-circle").attr("r",1e-6).style("fill",e=>this.getNodeColor(e)).style("stroke",e=>this.getNodeStrokeColor(e)).style("stroke-width",e=>this.isNodeDirectory(e)?2:1.5).style("cursor",e=>e.data&&("root"===e.data.type||e.data.isRoot||0===e.depth)?"default":"pointer").on("click",(e,t)=>{console.log("🔵 [CIRCLE] Click on circle element!",{nodeName:t?.data?.name,nodePath:t?.data?.path,hasOnNodeClick:"function"==typeof this.onNodeClick}),this.onNodeClick(e,t)}).on("mouseover",this.showTooltip).on("mouseout",this.hideTooltip),s.filter(e=>this.isNodeDirectory(e)).append("text").attr("class","expand-icon").attr("x",0).attr("y",0).attr("text-anchor","middle").attr("dominant-baseline","central").text(e=>"loading"===e.data.loaded?"⟳":!0===e.data.loaded&&e.children?"▼":"▶").style("font-size","10px").style("pointer-events","none"),s.append("text").attr("class",e=>{const t="node-label";return 0===e.depth?(console.log(`📝 [TEXT] ✅ Adding horizontal-text class to root: ${e.data.name}`),`${t} horizontal-text`):t}).attr("dy",".35em").attr("x",e=>this.isRadialLayout?0:0===e.depth||this.horizontalNodes.has(e.data.path)?(console.log(`📝 [TEXT] ✅ HORIZONTAL positioning for: ${e.data.name} (depth: ${e.depth}, path: ${e.data.path})`),console.log(`📝 [TEXT] ✅ Root check: depth === 0 = ${0===e.depth}`),console.log(`📝 [TEXT] ✅ Horizontal set check: ${this.horizontalNodes.has(e.data.path)}`),0):(console.log(`📝 [TEXT] Positioning vertical text for: ${e.data.name} (depth: ${e.depth}, path: ${e.data.path})`),e.children||e._children?-13:13)).attr("y",e=>0===e.depth||this.horizontalNodes.has(e.data.path)?-20:0).attr("text-anchor",e=>this.isRadialLayout?"start":0===e.depth||this.horizontalNodes.has(e.data.path)?"middle":e.children||e._children?"end":"start").text(e=>{const t=e.data.name||"";return t.length>20?t.substring(0,17)+"...":t}).style("fill-opacity",1e-6).style("font-size","12px").style("font-family",'-apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, sans-serif').style("text-shadow","1px 1px 2px rgba(255,255,255,0.8), -1px -1px 2px rgba(255,255,255,0.8)").style("writing-mode",e=>0===e.depth?(console.log(`📝 [TEXT] ✅ Setting horizontal writing-mode for root: ${e.data.name}`),"horizontal-tb"):null).style("text-orientation",e=>0===e.depth?(console.log(`📝 [TEXT] ✅ Setting mixed text-orientation for root: ${e.data.name}`),"mixed"):null).on("click",(e,t)=>{console.log("📝 [LABEL] Click on text label!",{nodeName:t?.data?.name,nodePath:t?.data?.path,hasOnNodeClick:"function"==typeof this.onNodeClick}),this.onNodeClick(e,t)}).style("cursor",e=>e.data&&("root"===e.data.type||e.data.isRoot||0===e.depth)?"default":"pointer"),s.filter(e=>!this.isNodeDirectory(e)).append("text").attr("class","node-icon").attr("dy",".35em").attr("x",0).attr("text-anchor","middle").text(e=>this.getNodeIcon(e)).style("font-size","10px").style("fill","white").on("click",this.onNodeClick).style("cursor","pointer"),s.filter(e=>this.isNodeDirectory(e)&&e.data.children).append("text").attr("class","item-count-badge").attr("x",12).attr("y",-8).attr("text-anchor","middle").text(e=>{const t=e.data.children?e.data.children.length:0;return t>0?t:""}).style("font-size","9px").style("opacity",.7).on("click",this.onNodeClick).style("cursor","pointer");const a=s.merge(i);a.on("click",(e,t)=>{console.log("🟡 [NODE-UPDATE] Click on updated node!",{nodeName:t?.data?.name,nodePath:t?.data?.path,hasOnNodeClick:"function"==typeof this.onNodeClick,thisContext:this}),this.onNodeClick(e,t)}),a.selectAll("circle").on("click",this.onNodeClick),a.selectAll("text").on("click",this.onNodeClick),a.transition().duration(this.duration).attr("transform",e=>{if(this.isRadialLayout){const[t,o]=this.radialPoint(e.x,e.y);return`translate(${t},${o})`}return`translate(${e.y},${e.x})`}),a.attr("class",e=>{let t=["node","code-node"];return this.isNodeDirectory(e)?(t.push("directory"),!0===e.data.loaded&&e.children&&t.push("expanded"),"loading"===e.data.loaded&&t.push("loading"),e.data.children&&0===e.data.children.length&&t.push("empty")):"file"===e.data.type&&t.push("file"),t.join(" ")}),a.select("circle.node-circle").attr("r",e=>this.isNodeDirectory(e)?10:8).style("fill",e=>this.getNodeColor(e)),a.select(".expand-icon").text(e=>"loading"===e.data.loaded?"⟳":!0===e.data.loaded&&e.children?"▼":"▶"),a.select(".item-count-badge").text(e=>{if(!this.isNodeDirectory(e))return"";const t=e.data.children?e.data.children.length:0;return t>0?t:""}).style("stroke",e=>this.getNodeStrokeColor(e)).attr("cursor","pointer");const r=this.isRadialLayout,l=this.horizontalNodes;a.select("text.node-label").style("fill-opacity",1).style("fill","#333").each(function(e){const t=d3.select(this);if(r){const o=180*e.x/Math.PI-90;o>90||o<-90?t.attr("transform",`rotate(${o+180})`).attr("x",-15).attr("text-anchor","end").attr("dy",".35em"):t.attr("transform",`rotate(${o})`).attr("x",15).attr("text-anchor","start").attr("dy",".35em")}else{0===e.depth||l.has(e.data.path)?t.attr("transform",null).attr("x",0).attr("y",-20).attr("text-anchor","middle").attr("dy",".35em"):t.attr("transform",null).attr("x",e.children||e._children?-13:13).attr("y",0).attr("text-anchor",e.children||e._children?"end":"start").attr("dy",".35em")}});const d=i.exit().transition().duration(this.duration).attr("transform",t=>{if(this.isRadialLayout){const[t,o]=this.radialPoint(e.x,e.y);return`translate(${t},${o})`}return`translate(${e.y},${e.x})`}).remove();d.select("circle").attr("r",1e-6),d.select("text.node-label").style("fill-opacity",1e-6),d.select("text.node-icon").style("fill-opacity",1e-6);const c=this.treeGroup.selectAll("path.link").data(n,e=>e.id);if(c.enter().insert("path","g").attr("class","link").attr("d",t=>{const o={x:e.x0,y:e.y0};return this.isRadialLayout?this.radialDiagonal(o,o):this.diagonal(o,o)}).style("fill","none").style("stroke","#ccc").style("stroke-width",2).merge(c).transition().duration(this.duration).attr("d",e=>this.isRadialLayout?this.radialDiagonal(e,e.parent):this.diagonal(e,e.parent)),c.exit().transition().duration(this.duration).attr("d",t=>{const o={x:e.x,y:e.y};return this.isRadialLayout?this.radialDiagonal(o,o):this.diagonal(o,o)}).remove(),o.forEach(e=>{e.x0=e.x,e.y0=e.y}),this.zoom){const e=d3.zoomTransform(this.svg.node());1!==e.k&&this.adjustTextSizeForZoom(e.k)}}centerOnNode(e){console.log("[CodeTree] centerOnNode called but disabled - no centering will occur")}centerOnNodeRadial(e){console.log("[CodeTree] centerOnNodeRadial called but disabled - no centering will occur")}highlightActiveNode(e){const t=this.treeGroup.selectAll("circle.node-circle");t.classed("active",!1).classed("parent-context",!1),t.transition().duration(300).attr("r",8).style("stroke",null).style("stroke-width",null).style("opacity",null),this.treeGroup.selectAll("text.node-label").style("font-weight","normal").style("font-size","12px");const o=this.treeGroup.selectAll("g.node").filter(t=>t===e).select("circle.node-circle");o.classed("active",!0),o.transition().duration(300).attr("r",20).style("stroke","#3b82f6").style("stroke-width",5).style("filter","drop-shadow(0 0 15px rgba(59, 130, 246, 0.6))"),this.treeGroup.selectAll("g.node").filter(t=>t===e).select("text.node-label").style("font-weight","bold").style("font-size","14px"),this.activeNode=e}addLoadingPulse(e){const t=this.treeGroup.selectAll("g.node").filter(t=>t===e).select("circle.node-circle");this.loadingNodes.add(e.data.path),t.classed("loading-pulse",!0),t.style("fill","#fb923c");const o=()=>{this.loadingNodes.has(e.data.path)&&t.transition().duration(600).attr("r",14).style("opacity",.6).transition().duration(600).attr("r",10).style("opacity",1).on("end",()=>{this.loadingNodes.has(e.data.path)&&o()})};o()}removeLoadingPulse(e){const t=this.treeGroup.selectAll("g.node").filter(t=>t===e).select("circle.node-circle");t.classed("loading-pulse",!1),t.interrupt().transition().duration(300).attr("r",this.activeNode===e?20:8).style("opacity",1).style("fill",e=>this.getNodeColor(e))}showWithParent(e){if(!e.parent)return;const t=this.treeGroup.selectAll("g.node").filter(t=>t===e.parent).select("circle.node-circle");t.classed("parent-context",!0),t.style("stroke","#10b981").style("stroke-width",3).style("opacity",.8)}onNodeClick(e,t){const o=Date.now()+Math.random();if(console.log(`🖱️🖱️🖱️ [NODE CLICK] onNodeClick method called! (ID: ${o}):`,{thisContext:this,isBound:"CodeTree"===this.constructor.name,name:t?.data?.name,path:t?.data?.path,type:t?.data?.type,loaded:t?.data?.loaded,hasChildren:!(!t?.children&&!t?._children),dataChildren:t?.data?.children?.length||0,loadingNodesSize:this.loadingNodes?this.loadingNodes.size:"undefined"}),this.updateStructuredData(t),e)try{"function"==typeof e.stopPropagation&&e.stopPropagation()}catch(i){console.error("[CodeTree] ERROR calling stopPropagation:",i)}if(!t)return void console.error("[CodeTree] ERROR: d is null/undefined, cannot continue");if(t.data&&("root"===t.data.type||t.data.isRoot||0===t.depth))return void console.log("🚫 [ROOT CLICK] Ignoring click on root node:",t.data.name);if(!t.data)return void console.error("[CodeTree] ERROR: d.data is null/undefined, cannot continue");try{"function"==typeof this.highlightActiveNode?this.highlightActiveNode(t):console.error("[CodeTree] highlightActiveNode is not a function!")}catch(i){console.error("[CodeTree] ERROR during highlightActiveNode:",i,i.stack)}try{"function"==typeof this.showWithParent?this.showWithParent(t):console.error("[CodeTree] showWithParent is not a function!")}catch(i){console.error("[CodeTree] ERROR during showWithParent:",i,i.stack)}if(this.isNodeDirectory(t)&&!t.data.loaded)try{"function"==typeof this.addLoadingPulse?this.addLoadingPulse(t):console.error("[CodeTree] addLoadingPulse is not a function!")}catch(i){console.error("[CodeTree] ERROR during addLoadingPulse:",i,i.stack)}const n=this.getSelectedLanguages();console.log("🔍 [LANGUAGE] Selected languages:",n);document.getElementById("ignore-patterns");if(console.log("🔍 [LOAD CHECK]",{type:t.data.type,loaded:t.data.loaded,loadedType:typeof t.data.loaded,isDirectory:"directory"===t.data.type||"root"===t.data.type,notLoaded:!t.data.loaded,shouldLoad:("directory"===t.data.type||"root"===t.data.type)&&!t.data.loaded}),"directory"!==t.data.type&&"root"!==t.data.type&&!t.data.isDirectory||t.data.loaded)if("file"===t.data.type){if(console.log("📄 [FILE CLICK] File clicked:",{fileName:t.data.name,filePath:t.data.path,analyzed:t.data.analyzed}),this.displayFileInDataViewer(t),!t.data.analyzed){const e=this.detectLanguage(t.data.path);if(console.log("🔍 [FILE ANALYSIS] Language check:",{fileName:t.data.name,filePath:t.data.path,detectedLanguage:e,selectedLanguages:n,isLanguageSelected:n.includes(e),shouldAnalyze:n.includes(e)||"unknown"===e}),!n.includes(e)&&"unknown"!==e)return void console.warn("⚠️ [FILE ANALYSIS] Skipping AST analysis for file:",{fileName:t.data.name,detectedLanguage:e,selectedLanguages:n,reason:`${e} not in selected languages`})}this.addLoadingPulse(t),t.data.analyzed="loading";const o=this.ensureFullPath(t.data.path);setTimeout(()=>{if(console.log("🚀 [FILE ANALYSIS] Sending analysis request:",{fileName:t.data.name,originalPath:t.data.path,fullPath:o,hasSocket:!!this.socket,socketConnected:this.socket?.connected}),this.socket&&this.socket.connected){console.log("📡 [FILE ANALYSIS] Using SocketIO for analysis:",{event:"code:analyze:file",path:o,socketConnected:this.socket.connected,socketId:this.socket.id}),this.socket.emit("code:analyze:file",{path:o});const n=setTimeout(()=>{console.warn("⏰ [FILE ANALYSIS] SocketIO timeout, trying HTTP fallback for:",o),this.analyzeFileHTTP(o,t.data.name,d3.select(e.target.closest("g")))},5e3);this.analysisTimeouts||(this.analysisTimeouts=new Map),this.analysisTimeouts.set(o,n),this.updateBreadcrumb(`Analyzing ${t.data.name}...`,"info"),this.showNotification(`Analyzing: ${t.data.name}`,"info")}else console.log("🔄 [FILE ANALYSIS] SocketIO unavailable, using HTTP fallback"),this.updateBreadcrumb(`Analyzing ${t.data.name}...`,"info"),this.showNotification(`Analyzing: ${t.data.name}`,"info"),this.analyzeFileHTTP(o,t.data.name,d3.select(e.target.closest("g")))},100)}else if(this.isNodeDirectory(t)&&!0===t.data.loaded){if(t.children)t._children=t.children,t.children=null,t.data.expanded=!1;else if(t._children)t.children=t._children,t._children=null,t.data.expanded=!0;else if(t.data.children&&t.data.children.length>0){this.root=d3.hierarchy(this.treeData);const e=this.findD3NodeByPath(t.data.path);e&&(e.children=e._children||e.children,e._children=null,e.data.expanded=!0)}this.update(this.root)}else(t.children||t._children)&&(t.children?(t._children=t.children,t.children=null,t.data.expanded=!1):(t.children=t._children,t._children=null,t.data.expanded=!0),this.update(t));else{console.log("✅ [SUBDIRECTORY LOADING] Load check passed, proceeding with loading logic"),console.log("🔍 [SUBDIRECTORY LOADING] Initial loading state:",{loadingNodesSize:this.loadingNodes?this.loadingNodes.size:"undefined",loadingNodesContent:Array.from(this.loadingNodes||[])});try{console.log("🔍 [SUBDIRECTORY LOADING] Checking for duplicates:",{path:t.data.path,pathType:typeof t.data.path,loadingNodesType:typeof this.loadingNodes,loadingNodesSize:this.loadingNodes?this.loadingNodes.size:"undefined",hasMethod:this.loadingNodes&&"function"==typeof this.loadingNodes.has});const e=this.loadingNodes&&this.loadingNodes.has(t.data.path);console.log("🔍 [SUBDIRECTORY LOADING] Duplicate check result:",{isDuplicate:e,loadingNodesContent:Array.from(this.loadingNodes||[]),pathBeingChecked:t.data.path}),e&&(console.warn("⚠️ [SUBDIRECTORY LOADING] Duplicate request detected, but proceeding anyway:",{path:t.data.path,name:t.data.name,loadingNodesSize:this.loadingNodes.size,loadingNodesContent:Array.from(this.loadingNodes),pathInSet:this.loadingNodes.has(t.data.path)}),this.loadingNodes.delete(t.data.path),console.log("🧹 [SUBDIRECTORY LOADING] Removed duplicate entry, proceeding with fresh request")),console.log("✅ [SUBDIRECTORY LOADING] No duplicate request, proceeding to mark as loading"),t.data.loaded="loading",this.loadingNodes.add(t.data.path);const o=this.ensureFullPath(t.data.path);console.log("🚀 [SUBDIRECTORY LOADING] Attempting to load:",{originalPath:t.data.path,fullPath:o,nodeType:t.data.type,loaded:t.data.loaded,hasSocket:!!this.socket,workingDir:this.getWorkingDirectory()});setTimeout(()=>{console.log("📡 [SUBDIRECTORY LOADING] Using REST API for directory:",{originalPath:t.data.path,fullPath:o,apiUrl:`${window.location.origin}/api/directory?path=${encodeURIComponent(o)}`,loadingNodesSize:this.loadingNodes.size,loadingNodesContent:Array.from(this.loadingNodes)});const e=`${window.location.origin}/api/directory?path=${encodeURIComponent(o)}`;if(fetch(e).then(e=>{if(!e.ok)throw new Error(`HTTP ${e.status}: ${e.statusText}`);return e.json()}).then(e=>{console.log("✅ [SUBDIRECTORY LOADING] REST API response:",{data:e,pathToDelete:t.data.path,loadingNodesBefore:Array.from(this.loadingNodes)});const o=this.loadingNodes.delete(t.data.path);t.data.loaded=!0,console.log("🧹 [SUBDIRECTORY LOADING] Cleanup result:",{pathDeleted:t.data.path,wasDeleted:o,loadingNodesAfter:Array.from(this.loadingNodes)});const n=this.findD3NodeByPath(t.data.path);if(n&&this.removeLoadingPulse(n),e.exists&&e.is_directory&&e.contents){const o=this.findNodeByPath(t.data.path);if(o){if(console.log("🔧 [SUBDIRECTORY LOADING] Creating children with paths:",e.contents.map(e=>({name:e.name,path:e.path}))),o.children=e.contents.map(e=>({name:e.name,path:e.path,type:e.is_directory?"directory":"file",loaded:!e.is_directory&&void 0,analyzed:!!e.is_directory&&void 0,expanded:!1,children:e.is_directory?[]:void 0})),o.loaded=!0,o.expanded=!0,this.root&&this.svg){const o=this.root;this.root=d3.hierarchy(this.treeData),this.root.x0=this.height/2,this.root.y0=0,this.preserveExpansionState(o,this.root);const n=this.findD3NodeByPath(t.data.path);n&&n.children&&n.children.length>0&&(n._children=null,n.data.expanded=!0),this.update(n||this.root),n&&e.contents.length>0&&setTimeout(()=>{this.focusOnDirectory(n)},500)}this.updateBreadcrumb(`Loaded ${e.contents.length} items`,"success"),this.showNotification(`Loaded ${e.contents.length} items from ${t.data.name}`,"success")}}else this.showNotification(`Directory ${t.data.name} is empty or inaccessible`,"warning")}).catch(e=>{console.error("❌ [SUBDIRECTORY LOADING] REST API error:",{error:e.message,stack:e.stack,pathToDelete:t.data.path,loadingNodesBefore:Array.from(this.loadingNodes)});const o=this.loadingNodes.delete(t.data.path);t.data.loaded=!1,console.log("🧹 [SUBDIRECTORY LOADING] Error cleanup:",{pathDeleted:t.data.path,wasDeleted:o,loadingNodesAfter:Array.from(this.loadingNodes)});const n=this.findD3NodeByPath(t.data.path);n&&this.removeLoadingPulse(n),this.showNotification(`Failed to load ${t.data.name}: ${e.message}`,"error")}),this.updateBreadcrumb(`Loading ${t.data.name}...`,"info"),this.showNotification(`Loading directory: ${t.data.name}`,"info"),!window.fetch){console.error("❌ [SUBDIRECTORY LOADING] No WebSocket connection available!"),this.showNotification("Cannot load directory: No connection","error"),this.loadingNodes.delete(t.data.path);const e=this.findD3NodeByPath(t.data.path);e&&this.removeLoadingPulse(e),t.data.loaded=!1}},100)}catch(i){console.error("❌ [SUBDIRECTORY LOADING] Error in directory loading logic:",{error:i.message,stack:i.stack,path:t.data.path,nodeData:t.data}),this.showNotification(`Error loading directory: ${i.message}`,"error")}}this.selectedNode=t;try{this.highlightNode(t)}catch(i){console.error("[CodeTree] ERROR during highlightNode:",i)}}ensureFullPath(e){if(console.log("🔗 ensureFullPath called with:",e),!e)return e;if(e.startsWith("/"))return console.log(" → Already absolute, returning:",e),e;const t=this.getWorkingDirectory();if(console.log(" → Working directory:",t),!t)return console.log(" → No working directory, returning original:",e),e;if("."===e)return console.log(" → Root path detected, returning working dir:",t),t;if(e===t)return console.log(" → Path equals working directory, returning:",t),t;const o=`${t}/${e}`.replace(/\/+/g,"/");return console.log(" → Combining with working dir, result:",o),o}highlightNode(e){this.treeGroup.selectAll("circle.node-circle").style("stroke-width",2).classed("selected",!1),this.treeGroup.selectAll("circle.node-circle").filter(t=>t===e).style("stroke-width",4).classed("selected",!0)}diagonal(e,t){return`M ${e.y} ${e.x}\n C ${(e.y+t.y)/2} ${e.x},\n ${(e.y+t.y)/2} ${t.x},\n ${t.y} ${t.x}`}radialDiagonal(e,t){return d3.linkRadial().angle(e=>e.x).radius(e=>e.y)({source:e,target:t})}isNodeDirectory(e){const t=e.data||e;return"directory"===t.type||"root"===t.type||!0===t.isDirectory}getNodeColor(e){const t=e.data.type,o=e.data.complexity||1,n={root:"#6B7280",directory:"#3B82F6",file:"#10B981",module:"#8B5CF6",class:"#F59E0B",function:"#EF4444",method:"#EC4899"}[t]||"#6B7280";return o>10?d3.color(n).darker(.5):o>5?d3.color(n).darker(.25):n}getNodeStrokeColor(e){return"loading"===e.data.loaded||"loading"===e.data.analyzed?"#FCD34D":this.isNodeDirectory(e)&&!e.data.loaded?"#94A3B8":"file"!==e.data.type||e.data.analyzed?this.getNodeColor(e):"#CBD5E1"}getNodeIcon(e){return{root:"📦",directory:"📁",file:"📄",module:"📦",class:"C",function:"ƒ",method:"m"}[e.data.type]||"•"}showTooltip(e,t){if(!this.tooltip)return;const o=[];o.push(`<strong>${t.data.name}</strong>`),o.push(`Type: ${t.data.type}`),t.data.language&&o.push(`Language: ${t.data.language}`),t.data.complexity&&o.push(`Complexity: ${t.data.complexity}`),t.data.lines&&o.push(`Lines: ${t.data.lines}`),t.data.path&&o.push(`Path: ${t.data.path}`),this.isNodeDirectory(t)&&!t.data.loaded?o.push("<em>Click to explore contents</em>"):"file"!==t.data.type||t.data.analyzed||o.push("<em>Click to analyze file</em>"),this.tooltip.transition().duration(200).style("opacity",.9),this.tooltip.html(o.join("<br>")).style("left",e.pageX+10+"px").style("top",e.pageY-28+"px")}hideTooltip(){this.tooltip&&this.tooltip.transition().duration(500).style("opacity",0)}filterTree(){this.root&&(this.root.descendants().forEach(e=>{e.data._hidden=!1,"all"!==this.languageFilter&&"file"===e.data.type&&e.data.language!==this.languageFilter&&(e.data._hidden=!0),this.searchTerm&&(e.data.name.toLowerCase().includes(this.searchTerm)||(e.data._hidden=!0))}),this.update(this.root))}expandAll(){if(!this.root)return;const e=t=>{t._children&&(t.children=t._children,t._children=null),t.children&&t.children.forEach(e)};e(this.root),this.update(this.root),this.showNotification("All nodes expanded","info")}collapseAll(){if(!this.root)return;const e=t=>{t.children&&(t._children=t.children,t.children=null),t._children&&t._children.forEach(e)};this.root.children?.forEach(e),this.update(this.root),this.showNotification("All nodes collapsed","info")}focusOnDirectory(e){if(!e||"directory"!==e.data.type)return;console.log("🎯 [FOCUS] Focusing on directory:",e.data.path),this.focusedNode=e;const t={...e.data,name:`📁 ${e.data.name}`,children:e.data.children||[]},o=d3.hierarchy(t);o.x0=this.height/2,o.y0=0,this.originalRoot||(this.originalRoot=this.root),this.root=o,this.update(this.root),d3.select("#code-tree-container").classed("focused",!0),this.updateBreadcrumb(`Focused on: ${e.data.name}`,"info"),this.showNotification(`Focused on directory: ${e.data.name}`,"info"),this.addBackButton()}unfocusDirectory(){this.originalRoot&&(console.log("🔙 [FOCUS] Returning to full tree view"),this.root=this.originalRoot,this.originalRoot=null,this.focusedNode=null,this.update(this.root),d3.select("#code-tree-container").classed("focused",!1),this.removeBackButton(),this.updateBreadcrumb("Full tree view restored","success"),this.showNotification("Returned to full tree view","success"))}addBackButton(){d3.select("#tree-back-button").remove();const e=d3.select(".tree-controls-toolbar");e.empty()||e.insert("button",":first-child").attr("id","tree-back-button").attr("class","tree-control-btn back-btn").attr("title","Return to full tree view").text("← Back").on("click",()=>this.unfocusDirectory())}removeBackButton(){d3.select("#tree-back-button").remove()}resetZoom(){if(!this.svg||!this.zoom)return;const e=this.treeGroup.node().getBBox(),t=this.width,o=this.height,n=e.width,i=e.height,s=e.x+n/2,a=e.y+i/2;if(0===n||0===i)return;const r=.9*Math.min(t/n,o/i),l=[t/2-r*s,o/2-r*a];this.svg.transition().duration(750).call(this.zoom.transform,d3.zoomIdentity.translate(l[0],l[1]).scale(r)),this.showNotification("Zoom reset to fit tree","info")}zoomIn(){this.svg&&this.zoom&&this.svg.transition().duration(300).call(this.zoom.scaleBy,1.5)}zoomOut(){this.svg&&this.zoom&&this.svg.transition().duration(300).call(this.zoom.scaleBy,1/1.5)}updateZoomLevel(e){const t=document.getElementById("zoom-level-display");t&&(t.textContent=`${Math.round(100*e)}%`)}adjustTextSizeForZoom(e){if(!this.treeGroup)return;const t=1/e;this.treeGroup.selectAll("text").style("font-size",12*t+"px").attr("transform",function(){const e=(d3.select(this).attr("transform")||"").replace(/scale\([^)]*\)/g,"").trim();return e?`${e} scale(${t})`:`scale(${t})`}),this.treeGroup.selectAll(".expand-icon").style("font-size",12*t+"px").attr("transform",function(){const e=(d3.select(this).attr("transform")||"").replace(/scale\([^)]*\)/g,"").trim();return e?`${e} scale(${t})`:`scale(${t})`}),this.treeGroup.selectAll(".item-count-badge").style("font-size",10*t+"px").attr("transform",function(){const e=(d3.select(this).attr("transform")||"").replace(/scale\([^)]*\)/g,"").trim();return e?`${e} scale(${t})`:`scale(${t})`})}addZoomKeyboardShortcuts(){document.addEventListener("keydown",e=>{const t=document.getElementById("code-tab");if(t&&t.classList.contains("active")&&"INPUT"!==e.target.tagName&&"TEXTAREA"!==e.target.tagName&&(e.ctrlKey||e.metaKey))switch(e.key){case"=":case"+":e.preventDefault(),this.zoomIn();break;case"-":e.preventDefault(),this.zoomOut();break;case"0":e.preventDefault(),this.resetZoom()}})}isSourceFile(e){if(!e)return!1;return[".py",".js",".ts",".jsx",".tsx",".java",".cpp",".c",".h",".cs",".php",".rb",".go",".rs",".swift"].some(t=>e.toLowerCase().endsWith(t))}async showSourceViewer(e){if(console.log("📄 [SOURCE VIEWER] Starting showSourceViewer for:",e.data.path),console.log(" Node type:",e.data.type),console.log(" Content element available:",!!this.structuredDataContent),!this.structuredDataContent)return void console.error("❌ [SOURCE VIEWER] No content element to display source in!");const t=document.createElement("div");t.className="source-viewer",console.log("📦 [SOURCE VIEWER] Created source viewer container");const o=document.createElement("div");o.className="source-viewer-header",o.innerHTML=`\n <span>📄 ${e.data.name||"Source File"}</span>\n <div class="source-viewer-controls">\n <button class="source-control-btn" id="expand-all-source" title="Expand all">⬇</button>\n <button class="source-control-btn" id="collapse-all-source" title="Collapse all">⬆</button>\n </div>\n `;const n=document.createElement("div");n.className="source-viewer-content",n.id="source-viewer-content",t.appendChild(o),t.appendChild(n),console.log("🔨 [SOURCE VIEWER] Appending source viewer to content element..."),this.structuredDataContent.appendChild(t),console.log("✅ [SOURCE VIEWER] Source viewer added to DOM"),console.log(" Content element children count:",this.structuredDataContent.children.length),console.log(" Content element HTML preview:",this.structuredDataContent.innerHTML.substring(0,200)+"..."),document.getElementById("expand-all-source")?.addEventListener("click",()=>this.expandAllSource()),document.getElementById("collapse-all-source")?.addEventListener("click",()=>this.collapseAllSource());try{await this.loadSourceContent(e,n)}catch(i){console.error("Failed to load source content:",i),n.innerHTML='\n <div class="ast-data-placeholder">\n <div class="ast-placeholder-icon">❌</div>\n <div class="ast-placeholder-text">Failed to load source file</div>\n </div>\n '}}focusOnNode(e){console.log("[CodeTree] focusOnNode called but disabled - no focusing will occur")}getNodePath(e){const t=[];let o=e;for(;o;)o.data&&o.data.name&&t.unshift(o.data.name),o=o.parent;return t.join(" / ")}toggleLegend(){const e=document.getElementById("tree-legend");e&&("none"===e.style.display?e.style.display="block":e.style.display="none")}getWorkingDirectory(){if(window.dashboard&&window.dashboard.workingDirectoryManager)return window.dashboard.workingDirectoryManager.getCurrentWorkingDir();const e=document.getElementById("working-dir-path");if(e){const t=e.textContent.trim();if(t&&"Loading..."!==t&&"Not selected"!==t)return t}return null}showNoWorkingDirectoryMessage(){const e=document.getElementById("code-tree-container");if(!e)return;this.removeNoWorkingDirectoryMessage(),this.hideLoading();const t=document.createElement("div");t.id="no-working-dir-message",t.className="no-working-dir-message",t.innerHTML='\n <div class="message-icon">📁</div>\n <h3>No Working Directory Selected</h3>\n <p>Please select a working directory from the top menu to analyze code.</p>\n <button id="select-working-dir-btn" class="btn btn-primary">\n Select Working Directory\n </button>\n ',t.style.cssText="\n text-align: center;\n padding: 40px;\n color: #666;\n font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', Roboto, sans-serif;\n ";const o=t.querySelector(".message-icon");o&&(o.style.cssText="font-size: 48px; margin-bottom: 16px; opacity: 0.5;");const n=t.querySelector("h3");n&&(n.style.cssText="margin: 16px 0; color: #333; font-size: 20px;");const i=t.querySelector("p");i&&(i.style.cssText="margin: 16px 0; color: #666; font-size: 14px;");const s=t.querySelector("button");s&&(s.style.cssText="\n margin-top: 20px;\n padding: 10px 20px;\n background: #3b82f6;\n color: white;\n border: none;\n border-radius: 6px;\n cursor: pointer;\n font-size: 14px;\n transition: background 0.2s;\n ",s.addEventListener("mouseenter",()=>{s.style.background="#2563eb"}),s.addEventListener("mouseleave",()=>{s.style.background="#3b82f6"}),s.addEventListener("click",()=>{const e=document.getElementById("change-dir-btn");e?e.click():window.dashboard&&window.dashboard.workingDirectoryManager&&window.dashboard.workingDirectoryManager.showChangeDirDialog()})),e.appendChild(t),this.updateBreadcrumb("Please select a working directory","warning")}removeNoWorkingDirectoryMessage(){const e=document.getElementById("no-working-dir-message");e&&e.remove()}clearLoadingState(){console.log("🧹 [DEBUG] Clearing loading state:",{loadingNodesBefore:Array.from(this.loadingNodes),size:this.loadingNodes.size}),this.loadingNodes.clear(),this.resetLoadingFlags(this.treeData),console.log("✅ [DEBUG] Loading state cleared"),this.showNotification("Loading state cleared","info")}resetLoadingFlags(e){"loading"===e.loaded&&(e.loaded=!1),e.children&&e.children.forEach(e=>this.resetLoadingFlags(e))}exportTree(){const e={timestamp:(new Date).toISOString(),workingDirectory:this.getWorkingDirectory(),stats:this.stats,tree:this.treeData},t=new Blob([JSON.stringify(e,null,2)],{type:"application/json"}),o=URL.createObjectURL(t),n=document.createElement("a");n.href=o,n.download=`code-tree-${Date.now()}.json`,n.click(),URL.revokeObjectURL(o),this.showNotification("Tree exported successfully","success")}updateActivityTicker(e,t="info"){const o=document.getElementById("breadcrumb-content");if(o){const n="info"===t&&e.includes("...")?"⟳ ":"";o.innerHTML=`${n}${e}`,o.className=`breadcrumb-${t}`}}updateTicker(e,t="info"){const o=document.getElementById("code-tree-ticker");o&&(o.textContent=e,o.className=`ticker ticker-${t}`,"error"!==t&&setTimeout(()=>{o.style.opacity="0",setTimeout(()=>{o.style.opacity="1",o.textContent=""},300)},5e3))}initializeStructuredData(){if(console.log("🔄 [CODE TREE] Initializing structured data integration..."),this.structuredDataContent=document.getElementById("module-data-content"),!this.structuredDataContent)return console.warn("⏳ [CODE TREE] Structured data element not found yet, retrying in 500ms..."),void setTimeout(()=>{if(this.structuredDataContent=document.getElementById("module-data-content"),this.structuredDataContent)console.log("✅ [CODE TREE] Structured data integration initialized on retry"),console.log(" Target element:",this.structuredDataContent),console.log(" Parent element:",this.structuredDataContent.parentElement);else{console.error("❌ [CODE TREE] Structured data content element (#module-data-content) not found after retry!"),console.log("[CODE TREE] Checking DOM for available elements...");const e=document.querySelectorAll('[id*="module"], [id*="data"]');console.log(`[CODE TREE] Found ${e.length} elements with "module" or "data" in ID:`),e.forEach(e=>{console.log(` - #${e.id} (class: ${e.className}, parent: ${e.parentElement?.id||"no-parent"})`)});const t=document.querySelector(".module-viewer");if(t){console.log("[CODE TREE] Module viewer found, checking children...");const e=t.querySelector("#module-data-content");e?(console.log("[CODE TREE] Found module-data-content via query selector!"),this.structuredDataContent=e):console.log("[CODE TREE] Module data content not found in module viewer")}}},500);console.log("✅ [CODE TREE] Structured data integration initialized immediately"),console.log(" Target element:",this.structuredDataContent),console.log(" Parent element:",this.structuredDataContent.parentElement)}updateStructuredData(e){if(console.log("📝 [STRUCTURED DATA] updateStructuredData called"),!this.structuredDataContent)if(console.warn("⚠️ [STRUCTURED DATA] Content element not available, trying to find it..."),this.structuredDataContent=document.getElementById("module-data-content"),this.structuredDataContent)console.log("✅ [STRUCTURED DATA] Found element on retry");else{console.error("❌ [STRUCTURED DATA] Cannot find module-data-content element!");const e=document.querySelector(".module-viewer");if(!e)return void console.error("❌ [STRUCTURED DATA] Module viewer not found either, aborting update");if(this.structuredDataContent=e.querySelector("#module-data-content"),!this.structuredDataContent)return void console.error("❌ [STRUCTURED DATA] Still cannot find element, aborting update");console.log("✅ [STRUCTURED DATA] Found element via module-viewer query")}if(console.log("🔍 [STRUCTURED DATA] Updating with node:",{name:e?.data?.name,type:e?.data?.type,path:e?.data?.path,hasChildren:!(!e?.children&&!e?._children),dataChildren:e?.data?.children?.length||0,contentElement:this.structuredDataContent}),this.structuredDataContent.innerHTML="",console.log("🧹 [STRUCTURED DATA] Cleared previous content"),"file"===e.data.type&&this.isSourceFile(e.data.path))this.showSourceViewer(e);else{const t=e.children||e._children||[],o=e.data.children||[];t.length>0||o.length>0?this.showASTNodeChildren(e):"file"===e.data.type&&e.data.analyzed?this.showASTFileDetails(e):this.showASTNodeDetails(e)}}showASTNodeChildren(e){const t=e.children||e._children||[],o=e.data.children||[],n=t.length>0?t:o;if(0===n.length)return void this.showASTEmptyState("No children found");const i=document.createElement("div");i.className="structured-view-header",i.innerHTML=`<h4>${this.getNodeIcon(e.data.type)} ${e.data.name||"Node"} - Children (${n.length})</h4>`,this.structuredDataContent.appendChild(i),n.forEach((e,t)=>{const o=e.data||e,n=this.createASTDataViewerItem(o,t);this.structuredDataContent.appendChild(n)})}showASTFileDetails(e){const t=document.createElement("div");t.className="structured-view-header",t.innerHTML=`<h4>${this.getNodeIcon(e.data.type)} ${e.data.name||"File"} - Details</h4>`,this.structuredDataContent.appendChild(t);const o=[];e.data.language&&o.push({label:"Language",value:e.data.language}),e.data.lines&&o.push({label:"Lines",value:e.data.lines}),void 0!==e.data.complexity&&o.push({label:"Complexity",value:e.data.complexity}),e.data.size&&o.push({label:"Size",value:this.formatFileSize(e.data.size)}),0!==o.length?o.forEach((e,t)=>{const o=this.createASTDetailItem(e,t);this.structuredDataContent.appendChild(o)}):this.showASTEmptyState("No details available")}showASTNodeDetails(e){const t=document.createElement("div");t.className="structured-view-header",t.innerHTML=`<h4>${this.getNodeIcon(e.data.type)} ${e.data.name||"Node"} - Details</h4>`,this.structuredDataContent.appendChild(t);const o=[];o.push({label:"Type",value:e.data.type||"unknown"}),o.push({label:"Path",value:e.data.path||"unknown"}),e.data.line&&o.push({label:"Line",value:e.data.line}),o.forEach((e,t)=>{const o=this.createASTDetailItem(e,t);this.structuredDataContent.appendChild(o)})}createASTDataViewerItem(e,t){const o=document.createElement("div");o.className="ast-data-viewer-item",o.dataset.index=t;const n=document.createElement("div");n.className="ast-data-item-header";const i=document.createElement("div");i.className="ast-data-item-name",i.innerHTML=`${this.getNodeIcon(e.type)} ${e.name||"Unknown"}`;const s=document.createElement("div");s.className=`ast-data-item-type ${e.type||"unknown"}`,s.textContent=e.type||"unknown",n.appendChild(i),n.appendChild(s);const a=document.createElement("div");a.className="ast-data-item-details";const r=[];if(e.line&&r.push(`<span class="ast-data-item-line">Line ${e.line}</span>`),void 0!==e.complexity){const t=this.getComplexityLevel(e.complexity);r.push(`<span class="ast-data-item-complexity">\n <span class="ast-complexity-indicator ${t}"></span>\n Complexity: ${e.complexity}\n </span>`)}return e.docstring&&r.push(`<div style="margin-top: 4px; font-style: italic;">${e.docstring}</div>`),a.innerHTML=r.join(" "),o.appendChild(n),o.appendChild(a),o.addEventListener("click",()=>{this.selectASTDataViewerItem(o)}),o}createASTDetailItem(e,t){const o=document.createElement("div");o.className="ast-data-viewer-item",o.dataset.index=t;const n=document.createElement("div");n.className="ast-data-item-header";const i=document.createElement("div");i.className="ast-data-item-name",i.textContent=e.label;const s=document.createElement("div");return s.className="ast-data-item-details",s.textContent=e.value,n.appendChild(i),o.appendChild(n),o.appendChild(s),o}showASTEmptyState(e){this.structuredDataContent.innerHTML=`\n <div class="ast-data-placeholder">\n <div class="ast-placeholder-icon">📭</div>\n <div class="ast-placeholder-text">${e}</div>\n </div>\n `}selectASTDataViewerItem(e){const t=this.structuredDataContent.querySelector(".ast-data-viewer-item.selected");t&&t.classList.remove("selected"),e.classList.add("selected"),this.selectedASTItem=e}getNodeIcon(e){return{directory:"📁",file:"📄",class:"🏛️",function:"⚡",method:"🔧",variable:"📦",import:"📥",module:"📦"}[e]||"📄"}getComplexityLevel(e){return e<=5?"low":e<=10?"medium":"high"}formatFileSize(e){if(0===e)return"0 B";const t=Math.floor(Math.log(e)/Math.log(1024));return parseFloat((e/Math.pow(1024,t)).toFixed(1))+" "+["B","KB","MB","GB"][t]}async loadSourceContent(e,t){const o=await this.readSourceFile(e.data.path);if(!o)throw new Error("Could not read source file");const n=e.data.children||[];this.renderSourceWithAST(o,n,t,e)}async readSourceFile(e){try{console.log("📖 [SOURCE READER] Reading file:",e);const t=await fetch(`/api/file/read?path=${encodeURIComponent(e)}`);if(!t.ok){const o=await t.json();return console.error("Failed to read file:",o),this.generatePlaceholderSource(e)}const o=await t.json();return console.log("📖 [SOURCE READER] Read",o.lines,"lines from",o.name),o.content}catch(t){return console.error("Failed to read source file:",t),this.generatePlaceholderSource(e)}}generatePlaceholderSource(e){const t=e.split("/").pop();return t.endsWith(".py")?`"""\n${t}\nGenerated placeholder content for demonstration\n"""\n\nimport os\nimport sys\nfrom typing import List, Dict, Optional\n\nclass ExampleClass:\n """Example class with methods."""\n\n def __init__(self, name: str):\n """Initialize the example class."""\n self.name = name\n self.data = {}\n\n def process_data(self, items: List[str]) -> Dict[str, int]:\n """Process a list of items and return counts."""\n result = {}\n for item in items:\n result[item] = result.get(item, 0) + 1\n return result\n\n def get_summary(self) -> str:\n """Get a summary of the processed data."""\n if not self.data:\n return "No data processed"\n return f"Processed {len(self.data)} items"\n\ndef main():\n """Main function."""\n example = ExampleClass("demo")\n items = ["a", "b", "a", "c", "b", "a"]\n result = example.process_data(items)\n print(example.get_summary())\n return result\n\nif __name__ == "__main__":\n main()\n`:`// ${t}\n// Generated placeholder content for demonstration\n\nclass ExampleClass {\n constructor(name) {\n this.name = name;\n this.data = {};\n }\n\n processData(items) {\n const result = {};\n for (const item of items) {\n result[item] = (result[item] || 0) + 1;\n }\n return result;\n }\n\n getSummary() {\n if (Object.keys(this.data).length === 0) {\n return "No data processed";\n }\n return \`Processed \${Object.keys(this.data).length} items\`;\n }\n}\n\nfunction main() {\n const example = new ExampleClass("demo");\n const items = ["a", "b", "a", "c", "b", "a"];\n const result = example.processData(items);\n console.log(example.getSummary());\n return result;\n}\n\nmain();\n`}renderSourceWithAST(e,t,o,n){const i=e.split("\n"),s=this.createASTLineMap(t);console.log("🎨 [SOURCE RENDERER] Rendering source with AST:",{lines:i.length,astElements:t.length,astMap:Object.keys(s).length}),i.forEach((e,t)=>{const i=t+1,a=this.createSourceLine(e,i,s[i],n);o.appendChild(a)}),this.currentSourceContainer=o,this.currentASTElements=t}createASTLineMap(e){const t={};return e.forEach(e=>{e.line&&(t[e.line]||(t[e.line]=[]),t[e.line].push(e))}),t}createSourceLine(e,t,o,n){const i=document.createElement("div");i.className="source-line",i.dataset.lineNumber=t;const s=o&&o.length>0;s&&(i.classList.add("ast-element"),i.dataset.astElements=JSON.stringify(o));const a=this.isCollapsibleLine(e,o);a&&i.classList.add("collapsible");const r=document.createElement("span");r.className="line-number",r.textContent=t;const l=document.createElement("span");l.className="collapse-indicator",a?(l.classList.add("expanded"),l.addEventListener("click",e=>{e.stopPropagation(),this.toggleSourceSection(i)})):l.classList.add("none");const d=document.createElement("span");return d.className="line-content",d.innerHTML=this.applySyntaxHighlighting(e),s&&i.addEventListener("click",()=>{this.onSourceLineClick(i,o,n)}),i.appendChild(r),i.appendChild(l),i.appendChild(d),i}isCollapsibleLine(e,t){const o=e.trim();return!!(o.startsWith("def ")||o.startsWith("class ")||o.startsWith("async def "))||(!!(o.includes("function ")||o.includes("class ")||o.includes("=> {")||o.match(/^\s*\w+\s*\([^)]*\)\s*{/))||!!t&&t.some(e=>"function"===e.type||"class"===e.type||"method"===e.type||"FunctionDef"===e.type||"ClassDef"===e.type))}applySyntaxHighlighting(e,t="text"){let o=e.replace(/&/g,"&amp;").replace(/</g,"&lt;").replace(/>/g,"&gt;");const n=[];if("json"===t||this.currentFilePath?.endsWith(".json")){const e=/"([^"]+)"(?=\s*:)/g;let t;for(;null!==(t=e.exec(o));)n.push({start:t.index,end:t.index+t[0].length,replacement:`<span class="json-key">${t[0]}</span>`});const i=/:\s*"([^"]*)"/g;for(;null!==(t=i.exec(o));){const e=t[0].indexOf('"');n.push({start:t.index+e,end:t.index+t[0].length,replacement:`<span class="string">"${t[1]}"</span>`})}const s=/:\s*(-?\d+\.?\d*)/g;for(;null!==(t=s.exec(o));){const e=t[0].indexOf(t[1]);n.push({start:t.index+e,end:t.index+t[0].length,replacement:`<span class="number">${t[1]}</span>`})}const a=/\b(true|false|null)\b/g;for(;null!==(t=a.exec(o));)n.push({start:t.index,end:t.index+t[0].length,replacement:`<span class="literal">${t[0]}</span>`})}else{const e=/\b(def|class|import|from|if|else|elif|for|while|try|except|finally|with|as|return|yield|lambda|async|await|function|const|let|var|catch|export)\b/g;let t;for(;null!==(t=e.exec(o));)n.push({start:t.index,end:t.index+t[0].length,replacement:`<span class="keyword">${t[0]}</span>`});const i=/(["'`])([^"'`]*?)\1/g;for(;null!==(t=i.exec(o));)n.push({start:t.index,end:t.index+t[0].length,replacement:`<span class="string">${t[0]}</span>`});const s=/(#.*$|\/\/.*$)/gm;for(;null!==(t=s.exec(o));)n.push({start:t.index,end:t.index+t[0].length,replacement:`<span class="comment">${t[0]}</span>`})}n.sort((e,t)=>t.start-e.start);for(const i of n){const e=o.substring(0,i.start),t=o.substring(i.end);(!e.includes("<span")||e.lastIndexOf("</span>")>e.lastIndexOf("<span"))&&(o=e+i.replacement+t)}return o}toggleSourceSection(e){e.querySelector(".collapse-indicator").classList.contains("expanded")?this.collapseSourceSection(e):this.expandSourceSection(e)}collapseSourceSection(e){const t=e.querySelector(".collapse-indicator");t.classList.remove("expanded"),t.classList.add("collapsed"),parseInt(e.dataset.lineNumber);const o=e.parentElement,n=Array.from(o.children);let i=n.indexOf(e)+1;const s=this.getLineIndentation(e.querySelector(".line-content").textContent);for(;i<n.length;){const e=n[i],t=e.querySelector(".line-content").textContent,o=this.getLineIndentation(t);if(t.trim()&&o<=s)break;e.classList.add("collapsed-content"),i++}const a=document.createElement("div");a.className="source-line collapsed-placeholder",a.innerHTML='\n <span class="line-number"></span>\n <span class="collapse-indicator none"></span>\n <span class="line-content"> ... (collapsed)</span>\n ',e.insertAdjacentElement("afterend",a)}expandSourceSection(e){const t=e.querySelector(".collapse-indicator");t.classList.remove("collapsed"),t.classList.add("expanded");const o=e.parentElement;Array.from(o.children).forEach(e=>{e.classList.contains("collapsed-content")&&e.classList.remove("collapsed-content")});const n=e.nextElementSibling;n&&n.classList.contains("collapsed-placeholder")&&n.remove()}getLineIndentation(e){const t=e.match(/^(\s*)/);return t?t[1].length:0}autoExpandFileWithAST(e,t){if(console.log("🌳 [AST EXPANSION] Auto-expanding file with AST:",{filePath:e,hasChildren:!!(t&&t.children&&t.children.length>0)}),!t||!t.children||0===t.children.length)return void console.log("⚠️ [AST EXPANSION] No children to expand");if(!this.findD3NodeByPath(e))return void console.log("⚠️ [AST EXPANSION] D3 node not found for path:",e);this.root=d3.hierarchy(this.treeData);const o=this.findD3NodeByPath(e);if(o&&(o._children||o.children&&0===o.children.length)){o.children=o._children||o.children,o._children=null,o.data.expanded=!0,console.log("✅ [AST EXPANSION] Expanded file node to show AST elements:",{filePath:e,childrenCount:o.children?o.children.length:0}),this.update(this.root);const t=e.split("/").pop(),n=o.children?o.children.length:0;this.showNotification(`📊 ${t} - AST tree expanded with ${n} elements`,"success"),this.updateBreadcrumb(`${t} - Code structure visible in tree`,"success")}}displayFileInDataViewer(e){console.log("📊 [DATA VIEWER] Displaying file in data viewer:",{fileName:e.data.name,filePath:e.data.path,fileType:e.data.type});const t={file_path:e.data.path,name:e.data.name,type:"file",size:e.data.size||0,extension:this.getFileExtension(e.data.path),language:this.detectLanguage(e.data.path),operations:[{operation:"view",timestamp:(new Date).toISOString(),source:"code_tree_click"}],metadata:{clicked_from:"code_tree",node_type:e.data.type,has_ast:e.data.analyzed||!1,tree_path:this.getNodePath(e)}};window.unifiedDataViewer?(window.unifiedDataViewer.display(t,"file_operation"),console.log("✅ [DATA VIEWER] File data displayed in unified viewer")):console.warn("⚠️ [DATA VIEWER] UnifiedDataViewer not available");const o=document.querySelector(".module-data-header h5");if(o){const t=e.data.name,n=this.getFileIcon(e.data.path);o.innerHTML=`${n} File: ${t}`}setTimeout(()=>{this.offerFileViewerOption(e)},1e3)}offerFileViewerOption(e){if(!this.isTextFile(e.data.path))return;const t=e.data.name,o=document.createElement("div");o.className="file-viewer-offer",o.innerHTML=`\n <div class="offer-content">\n <span class="offer-text">📄 ${t} loaded in data viewer</span>\n <button class="offer-button" onclick="this.parentElement.parentElement.remove(); window.showFileViewerModal && window.showFileViewerModal('${e.data.path}')">\n 🔍 Open Full Viewer\n </button>\n <button class="offer-close" onclick="this.parentElement.parentElement.remove()">×</button>\n </div>\n `,o.style.cssText="\n position: fixed;\n top: 20px;\n right: 20px;\n background: #f8fafc;\n border: 1px solid #e2e8f0;\n border-radius: 8px;\n padding: 12px;\n box-shadow: 0 4px 12px rgba(0, 0, 0, 0.1);\n z-index: 1000;\n max-width: 300px;\n font-size: 14px;\n ";const n=document.createElement("style");n.textContent="\n .offer-content {\n display: flex;\n align-items: center;\n gap: 8px;\n }\n .offer-text {\n flex: 1;\n color: #4a5568;\n }\n .offer-button {\n background: #4299e1;\n color: white;\n border: none;\n border-radius: 4px;\n padding: 4px 8px;\n font-size: 12px;\n cursor: pointer;\n transition: background 0.2s;\n }\n .offer-button:hover {\n background: #3182ce;\n }\n .offer-close {\n background: none;\n border: none;\n color: #a0aec0;\n cursor: pointer;\n font-size: 16px;\n padding: 0;\n width: 20px;\n height: 20px;\n display: flex;\n align-items: center;\n justify-content: center;\n }\n .offer-close:hover {\n color: #718096;\n }\n ",document.head.appendChild(n),document.body.appendChild(o),setTimeout(()=>{o.parentElement&&o.remove()},5e3)}isTextFile(e){if(!e)return!1;const t=this.getFileExtension(e),o=["py","js","ts","jsx","tsx","html","css","json","md","txt","yml","yaml","xml","sql","sh","bash","dockerfile","makefile","gitignore","readme","cfg","conf","ini","toml","lock"];return o.includes(t)||o.includes(e.toLowerCase().split("/").pop())}getNodePath(e){const t=[];let o=e;for(;o;)o.data&&o.data.name&&t.unshift(o.data.name),o=o.parent;return t.join(" > ")}getFileExtension(e){if(!e)return"";const t=e.split(".");return t.length>1?t.pop().toLowerCase():""}getFileTypeDescription(e){if(!e)return"File";const t=this.getFileExtension(e),o=e.toLowerCase();if(o.endsWith("__init__.py"))return"Python package initialization";if("makefile"===o)return"Build configuration";if(o.includes("config")||o.includes("settings"))return"Configuration file";if(o.includes("test")||o.includes("spec"))return"Test file";return{py:"Python file",js:"JavaScript file",ts:"TypeScript file",jsx:"React component",tsx:"React TypeScript component",html:"HTML document",css:"Stylesheet",json:"JSON data",md:"Markdown document",txt:"Text file",yml:"YAML configuration",yaml:"YAML configuration",xml:"XML document",sql:"SQL script",sh:"Shell script",bash:"Bash script",toml:"TOML configuration",ini:"INI configuration"}[t]||"File"}getElementCounts(e){const t={classes:0,functions:0,methods:0,total:e.length};return e.forEach(e=>{"class"===e.type?(t.classes++,e.methods&&(t.methods+=e.methods.length)):"function"===e.type&&t.functions++}),t}formatElementSummary(e){const t=[];return e.classes>0&&t.push(`${e.classes} class${1!==e.classes?"es":""}`),e.functions>0&&t.push(`${e.functions} function${1!==e.functions?"s":""}`),e.methods>0&&t.push(`${e.methods} method${1!==e.methods?"s":""}`),0===t.length?"Structural elements for tree view":1===t.length?t[0]+" found":2===t.length?t.join(" and ")+" found":t.slice(0,-1).join(", ")+", and "+t[t.length-1]+" found"}getFileIcon(e){if(!e)return"📄";const t={py:"🐍",js:"📜",ts:"📘",jsx:"⚛️",tsx:"⚛️",html:"🌐",css:"🎨",json:"📋",md:"📝",txt:"📄",yml:"⚙️",yaml:"⚙️",xml:"📰",sql:"🗃️",sh:"🐚",bash:"🐚",dockerfile:"🐳",makefile:"🔨",gitignore:"🚫",readme:"📖"};return t[this.getFileExtension(e)]||t[e.toLowerCase().split("/").pop()]||"📄"}onSourceLineClick(e,t,o){console.log("🎯 [SOURCE LINE CLICK] Line clicked:",{line:e.dataset.lineNumber,astElements:t.length}),this.highlightSourceLine(e),t.length>0&&this.showASTElementDetails(t[0],o),e.classList.contains("collapsible")&&this.toggleSourceSection(e)}highlightSourceLine(e){if(this.currentSourceContainer){this.currentSourceContainer.querySelectorAll(".source-line").forEach(e=>e.classList.remove("highlighted"))}e.classList.add("highlighted")}showASTElementDetails(e,t){console.log("📋 [AST DETAILS] Showing details for:",e)}expandAllSource(){if(!this.currentSourceContainer)return;this.currentSourceContainer.querySelectorAll(".source-line.collapsible").forEach(e=>{e.querySelector(".collapse-indicator").classList.contains("collapsed")&&this.expandSourceSection(e)})}collapseAllSource(){if(!this.currentSourceContainer)return;this.currentSourceContainer.querySelectorAll(".source-line.collapsible").forEach(e=>{e.querySelector(".collapse-indicator").classList.contains("expanded")&&this.collapseSourceSection(e)})}}window.CodeTree=e,document.addEventListener("DOMContentLoaded",()=>{document.getElementById("code-tree-container")&&(window.codeTree=new e,window.debugCodeTree={clearLoadingState:()=>window.codeTree?.clearLoadingState(),showLoadingNodes:()=>(console.log("Current loading nodes:",Array.from(window.codeTree?.loadingNodes||[])),Array.from(window.codeTree?.loadingNodes||[])),resetTree:()=>{window.codeTree&&(window.codeTree.clearLoadingState(),window.codeTree.initializeTreeData(),console.log("Tree reset complete"))},focusOnPath:e=>{if(window.codeTree){const t=window.codeTree.findD3NodeByPath(e);t?(window.codeTree.focusOnDirectory(t),console.log("Focused on:",e)):console.log("Node not found:",e)}},unfocus:()=>window.codeTree?.unfocusDirectory()},document.addEventListener("click",e=>{e.target.matches('[data-tab="code"]')&&setTimeout(()=>{window.codeTree&&!window.codeTree.initialized?window.codeTree.initialize():window.codeTree&&window.codeTree.renderWhenVisible()},100)}))});
2
- //# sourceMappingURL=code-tree.js.map
@@ -1,2 +0,0 @@
1
- class e{constructor(){this.container=null,this.svg=null,this.initialized=!1,this.fileActivity=new Map,this.sessions=new Map,this.currentSession=null,this.treeData=null,this.d3Tree=null,this.d3Root=null,this.selectedNode=null,this.width=800,this.height=600,this.nodeRadius=5,this.renderInProgress=!1,this.containerObserver=null}initialize(){if(console.log("[CodeViewer] initialize() called"),this.initialized)console.log("[CodeViewer] Already initialized, skipping");else{console.log("[CodeViewer] Starting initialization...");try{this.setupContainer(),console.log("[CodeViewer] Container setup complete"),this.setupEventHandlers(),console.log("[CodeViewer] Event handlers setup complete"),this.subscribeToEvents(),console.log("[CodeViewer] Event subscription complete"),this.processExistingEvents(),console.log("[CodeViewer] Existing events processed"),this.initialized=!0,console.log("[CodeViewer] Initialization complete!")}catch(e){throw console.error("[CodeViewer] Error during initialization:",e),e}}}setupContainer(){const e=document.getElementById("claude-tree-container");e?(this.container=e,this.renderInterface()):console.error("File Tree container not found")}renderInterface(){if(!this.container)return void console.error("[CodeViewer] Container not found, cannot render interface");if(this.renderInProgress)return;const e=this.container.querySelector(".activity-tree-wrapper");this.container.querySelector(".file-tree-empty-state");const t=this.container.querySelector("#claude-activity-tree-svg");if(e&&t)return;this.renderInProgress=!0,this.containerObserver&&this.containerObserver.disconnect(),this.container.innerHTML="",this.container.innerHTML='\n <div class="activity-tree-wrapper" style="height: 100%; display: flex; flex-direction: column;">\n <div class="activity-controls" style="padding: 10px; border-bottom: 1px solid #ddd; background: #f9f9f9; display: flex; align-items: center; gap: 10px;">\n <button id="claude-expand-all-btn" class="control-btn" style="padding: 4px 8px; font-size: 0.9em;">Expand All</button>\n <button id="claude-collapse-all-btn" class="control-btn" style="padding: 4px 8px; font-size: 0.9em;">Collapse All</button>\n <button id="claude-reset-zoom-btn" class="control-btn" style="padding: 4px 8px; font-size: 0.9em;">Reset Zoom</button>\n <div class="stats" id="claude-tree-stats" style="margin-left: auto; font-size: 0.9em; color: #666;"></div>\n </div>\n <div class="tree-container" id="claude-tree-svg-container" style="flex: 1; overflow: hidden; position: relative; background: white;">\n <svg id="claude-activity-tree-svg" style="width: 100%; height: 100%;"></svg>\n </div>\n <div class="legend" style="padding: 5px 10px; border-top: 1px solid #ddd; background: #f9f9f9; font-size: 0.85em; display: flex; gap: 15px;">\n <span class="legend-item"><span style="color: #4CAF50;">●</span> File</span>\n <span class="legend-item"><span style="color: #2196F3;">●</span> Class</span>\n <span class="legend-item"><span style="color: #FF9800;">●</span> Function</span>\n <span class="legend-item"><span style="color: #9C27B0;">●</span> Method</span>\n <span class="legend-item"><span style="color: #F44336;">◆</span> Edited</span>\n <span class="legend-item"><span style="color: #4CAF50;">○</span> Viewed</span>\n </div>\n </div>\n ';const i=document.getElementById("claude-tree-svg-container");if(i){const e=i.getBoundingClientRect();this.width=e.width||800,this.height=e.height||600}this.renderInProgress=!1,this.containerObserver&&this.container&&this.containerObserver.observe(this.container,{childList:!0,subtree:!1})}renderContent(){this._showInternal()}show(){this._showInternal()}_showInternal(){console.log("[CodeViewer] _showInternal() called");const e=document.getElementById("claude-tree-container");if(!e)return void console.error("[CodeViewer] File Tree container not found!");console.log("[CodeViewer] Found container, current HTML length:",e.innerHTML.length),console.log("[CodeViewer] Container children:",e.children.length),this.refreshFromFileToolTracker();let t=!1;if(["#events-list",".events-list",".event-item",".no-events",'[id*="event"]','[class*="event"]'].forEach(i=>{const s=e.querySelectorAll(i);s.length>0&&(console.warn(`[CodeViewer] Found ${s.length} foreign elements matching '${i}', removing...`),s.forEach(e=>e.remove()),t=!0)}),t&&(console.warn("[CodeViewer] Foreign content removed, clearing container completely for fresh start"),e.innerHTML=""),e.setAttribute("data-owner","code-viewer"),e.setAttribute("data-tab-reserved","claude-tree"),e.setAttribute("data-component","CodeViewer"),this.container&&this.container===e||(this.container=e),this.initialized){const e=this.container.querySelector(".activity-tree-wrapper"),t=this.container.querySelector(".file-tree-empty-state");e||t||this.renderInterface()}else this.initialize();this.containerObserver||this.protectContainer(),this.setupControlHandlers();const i=document.getElementById("session-select");i&&(this.currentSession=i.value||null),this.buildTreeData(),this.renderTree(),this.updateStats()}protectContainer(){const e=document.getElementById("claude-tree-container");if(!e)return;this.containerObserver&&this.containerObserver.disconnect();let t=!1;this.containerObserver=new MutationObserver(i=>{for(const n of i){for(const i of n.addedNodes)if(i.nodeType===Node.ELEMENT_NODE){const n=i;if(n.classList?.contains("event-item")||n.classList?.contains("events-list")||n.classList?.contains("no-events")||"events-list"===n.id||"agents-list"===n.id||"tools-list"===n.id||"files-list"===n.id||n.textContent&&(n.textContent.includes("[hook]")||n.textContent.includes("hook.user_prompt")||n.textContent.includes("hook.pre_tool")||n.textContent.includes("hook.post_tool")||n.textContent.includes("Connect to Socket.IO")||n.textContent.includes("No events")||n.textContent.includes("No agent events")||n.textContent.includes("No tool events")||n.textContent.includes("No file operations"))||"DIV"===n.tagName&&!n.classList?.contains("activity-tree-wrapper")&&!n.classList?.contains("file-tree-empty-state")&&!n.classList?.contains("activity-controls")&&!n.classList?.contains("tree-container")&&!n.classList?.contains("legend")&&!n.classList?.contains("stats")&&!n.id?.startsWith("claude-")){try{i.remove()}catch(s){console.warn("[CodeViewer] Failed to remove unwanted node:",s)}t||this.renderInProgress||(t=!0,setTimeout(()=>{t=!1,e.querySelector(".activity-tree-wrapper")||e.querySelector(".file-tree-empty-state")||(this.renderInterface(),this.setupControlHandlers(),this.buildTreeData(),this.renderTree())},50))}}if("childList"===n.type&&n.removedNodes.length>0)for(const e of n.removedNodes)if(e.nodeType===Node.ELEMENT_NODE){const i=e;(i.classList?.contains("activity-tree-wrapper")||i.classList?.contains("file-tree-empty-state"))&&(t||this.renderInProgress||(t=!0,setTimeout(()=>{t=!1,this.renderInterface(),this.setupControlHandlers(),this.buildTreeData(),this.renderTree()},50)))}}}),this.containerObserver.observe(e,{childList:!0,subtree:!1})}setupControlHandlers(){const e=document.getElementById("session-select");e&&!e.hasAttribute("data-tree-listener")&&(e.setAttribute("data-tree-listener","true"),e.addEventListener("change",e=>{this.currentSession=e.target.value||null,this.isTabActive()&&(this.buildTreeData(),this.renderTree(),this.updateStats())}));const t=document.getElementById("claude-expand-all-btn");t&&!t.hasAttribute("data-listener")&&(t.setAttribute("data-listener","true"),t.addEventListener("click",()=>{this.expandAllNodes()}));const i=document.getElementById("claude-collapse-all-btn");i&&!i.hasAttribute("data-listener")&&(i.setAttribute("data-listener","true"),i.addEventListener("click",()=>{this.collapseAllNodes()}));const s=document.getElementById("claude-reset-zoom-btn");s&&!s.hasAttribute("data-listener")&&(s.setAttribute("data-listener","true"),s.addEventListener("click",()=>{this.resetZoom()}))}setupEventHandlers(){}subscribeToEvents(){window.socket&&(window.socket.on("claude_event",e=>{(this.isFileOperationEvent(e)||this.isDirectFileEvent(e))&&setTimeout(()=>{this.refreshFromFileToolTracker(),this.isTabActive()&&(this.buildTreeData(),this.renderTree(),this.updateStats())},100)}),window.socket.on("file:read",e=>{this.handleDirectFileEvent("Read",e)}),window.socket.on("file:write",e=>{this.handleDirectFileEvent("Write",e)}),window.socket.on("file:edit",e=>{this.handleDirectFileEvent("Edit",e)})),window.eventBus&&window.eventBus.on("claude_event",e=>{(this.isFileOperationEvent(e)||this.isDirectFileEvent(e))&&(this.processClaudeEvent(e),this.isTabActive()&&(this.buildTreeData(),this.renderTree(),this.updateStats()))})}isTabActive(){const e=document.getElementById("claude-tree-tab");return e&&e.classList.contains("active")}processExistingEvents(){if(console.log("[CodeViewer] processExistingEvents called"),window.dashboard&&window.dashboard.fileToolTracker)this.refreshFromFileToolTracker();else if(window.dashboard&&window.dashboard.eventStore){const e=window.dashboard.eventStore.getAllEvents();console.log("[CodeViewer] Fallback to eventStore, total events:",e.length);let t=0,i=0;e.forEach(e=>{"hook"===e.type&&console.log("[CodeViewer] Hook event:",{subtype:e.subtype,tool_name:e.data?.tool_name,timestamp:e.timestamp}),this.isFileOperationEvent(e)&&(t++,console.log("[CodeViewer] Found file operation event:",e),this.processClaudeEvent(e),i++)}),console.log("[CodeViewer] processExistingEvents summary:",{totalEvents:e.length,fileOperations:t,processed:i,currentFileActivitySize:this.fileActivity.size})}else console.log("[CodeViewer] No dashboard or eventStore available")}isFileOperationEvent(e){if("hook"===e.type&&("pre_tool"===e.subtype||"post_tool"===e.subtype)&&e.data&&e.data.tool_name){return["Read","Write","Edit","MultiEdit","NotebookEdit"].includes(e.data.tool_name)}return!1}isDirectFileEvent(e){return!!("file_operation"===e.type||e.tool&&["Read","Write","Edit","MultiEdit","NotebookEdit"].includes(e.tool))}handleDirectFileEvent(e,t){const i={type:"file_operation",tool:e,data:{tool_name:e,tool_parameters:t.parameters||t,tool_output:t.output||null,session_id:t.session_id||this.currentSession,working_directory:t.working_directory||"/"},timestamp:t.timestamp||(new Date).toISOString()};this.processClaudeEvent(i),this.isTabActive()&&(this.buildTreeData(),this.renderTree(),this.updateStats())}isFileOperation(e){return["Read","Write","Edit","MultiEdit","NotebookEdit"].includes(e.tool_name)}processClaudeEvent(e){if(!this.isFileOperationEvent(e)&&!this.isDirectFileEvent(e))return;let t,i,s,n,o,r,a;if(this.isFileOperationEvent(e)){const a=e.data||{};t=a.tool_name,i=a.tool_parameters||{},s=a.tool_output,n=e.timestamp||(new Date).toISOString(),o=e.session_id||a.session_id,r=a.working_directory||"/"}else if(this.isDirectFileEvent(e)){const a=e.data||e;t=e.tool||a.tool_name,i=a.tool_parameters||a.parameters||{},s=a.tool_output||a.output,n=e.timestamp||a.timestamp||(new Date).toISOString(),o=e.session_id||a.session_id,r=a.working_directory||"/"}a=i.file_path||i.notebook_path,this.processFileOperation({tool_name:t,tool_parameters:i,tool_output:s,timestamp:n,session_id:o,working_directory:r,filePath:a})}processEvent(e){if(!this.isFileOperation(e))return;const{tool_name:t,tool_parameters:i,tool_output:s,timestamp:n,session_id:o,working_directory:r}=e,a=i?.file_path||i?.notebook_path;this.processFileOperation({tool_name:t,tool_parameters:i,tool_output:s,timestamp:n,session_id:o,working_directory:r,filePath:a})}processFileOperation({tool_name:e,tool_parameters:t,tool_output:i,timestamp:s,session_id:n,working_directory:o,filePath:r}){if(!r)return;n&&!this.sessions.has(n)&&(this.sessions.set(n,{id:n,working_directory:o||"/",files:new Set}),this.updateSessionList()),this.fileActivity.has(r)||this.fileActivity.set(r,{path:r,operations:[],sessions:new Set,working_directories:new Set,lastContent:null,astPaths:[]});const a=this.fileActivity.get(r);if(a.operations.push({type:e,timestamp:s,parameters:t,output:i,session_id:n}),n){a.sessions.add(n);const e=this.sessions.get(n);e&&e.files.add(r)}if(o&&a.working_directories.add(o),"Write"===e&&t.content)a.lastContent=t.content,a.astPaths=this.extractASTPaths(t.content,r);else if("Read"===e&&i?.content)a.lastContent=i.content,a.astPaths=this.extractASTPaths(i.content,r);else if("Edit"===e&&a.lastContent){const e=t.old_string,i=t.new_string;e&&i&&(a.lastContent=a.lastContent.replace(e,i),a.astPaths=this.extractASTPaths(a.lastContent,r))}}extractASTPaths(e,t){if(!e||"string"!=typeof e)return[];const i=t.split(".").pop()?.toLowerCase(),s=[];if("py"===i){const t=/^class\s+(\w+)/gm,i=/^def\s+(\w+)/gm,n=/^\s{4,}def\s+(\w+)/gm;let o;for(;null!==(o=t.exec(e));)s.push({name:o[1],type:"class"});for(;null!==(o=i.exec(e));)s.push({name:o[1],type:"function"});for(;null!==(o=n.exec(e));)s.some(e=>e.name===o[1])||s.push({name:o[1],type:"method"})}else if("js"===i||"jsx"===i||"ts"===i||"tsx"===i){const t=/class\s+(\w+)/g,i=/function\s+(\w+)/g,n=/const\s+(\w+)\s*=\s*\([^)]*\)\s*=>/g;let o;for(;null!==(o=t.exec(e));)s.push({name:o[1],type:"class"});for(;null!==(o=i.exec(e));)s.push({name:o[1],type:"function"});for(;null!==(o=n.exec(e));)s.push({name:o[1],type:"function"})}return s}buildTreeData(){const e={name:`Session: ${(this.currentSession||"current-session").substring(0,8)+"..."}`,type:"root",children:[]};if(!this.fileActivity||0===this.fileActivity.size)return e.children.push({name:"(No file operations yet)",type:"placeholder",children:[]}),this.treeData=e,void console.log("[CodeViewer] Built minimal tree with session root");const t=new Map;for(const[i,s]of this.fileActivity.entries()){if(this.currentSession&&!s.sessions.has(this.currentSession))continue;const e=Array.from(s.working_directories)[0]||"/";t.has(e)||t.set(e,{name:e.split("/").pop()||e,path:e,type:"directory",children:[]});const n=i.split("/").pop(),o=s.operations.some(e=>"Edit"===e.type||"Write"===e.type),r={name:n,path:i,type:"file",edited:o,operations:s.operations.length,children:[]};s.astPaths.length>0&&s.astPaths.forEach(e=>{r.children.push({name:e.name,type:e.type,path:`${i}#${e.name}`,children:[]})}),t.get(e).children.push(r)}e.children=Array.from(t.values()),1===e.children.length&&"/"===e.children[0].path&&(e.children=e.children[0].children),this.treeData=e}renderTree(){if(!this.treeData||!this.container)return;const e=document.getElementById("claude-activity-tree-svg");if(!e)return void console.warn("[CodeViewer] SVG element not found, skipping tree render");const t=d3.select(e);if(t.empty())return void console.warn("[CodeViewer] D3 could not select SVG element");t.selectAll("*").remove();const i=document.getElementById("claude-tree-svg-container");if(i){const e=i.getBoundingClientRect();this.width=e.width||800,this.height=e.height||600}const s=t.append("g"),n=d3.zoom().scaleExtent([.1,4]).on("zoom",e=>{s.attr("transform",e.transform)});t.call(n);const o=d3.tree().size([this.height-100,this.width-200]);this.d3Root=d3.hierarchy(this.treeData),o(this.d3Root),s.selectAll(".link").data(this.d3Root.links()).enter().append("path").attr("class","link").attr("d",d3.linkHorizontal().x(e=>e.y+100).y(e=>e.x+50)).style("fill","none").style("stroke","#ccc").style("stroke-width",1);const r=s.selectAll(".node").data(this.d3Root.descendants()).enter().append("g").attr("class","node").attr("transform",e=>`translate(${e.y+100},${e.x+50})`);r.append("circle").attr("r",this.nodeRadius).style("fill",e=>this.getNodeColor(e.data)).style("stroke",e=>e.data.edited?"#F44336":"#999").style("stroke-width",e=>e.data.edited?2:1).style("cursor","pointer").on("click",(e,t)=>this.handleNodeClick(e,t)),r.append("text").attr("dy",".35em").attr("x",e=>e.children?-10:10).style("text-anchor",e=>e.children?"end":"start").style("font-size","12px").style("cursor","pointer").text(e=>e.data.name).on("click",(e,t)=>this.handleNodeClick(e,t)),this.d3Tree={svg:t,g:s,zoom:n}}getNodeColor(e){switch(e.type){case"root":return"#666";case"directory":return"#FFC107";case"file":return"#4CAF50";case"class":return"#2196F3";case"function":return"#FF9800";case"method":return"#9C27B0";default:return"#999"}}handleNodeClick(e,t){e.stopPropagation(),t.children?(t._children=t.children,t.children=null):t._children&&(t.children=t._children,t._children=null),this.renderTree(),this.selectedNode=t,"file"===t.data.type&&this.fileActivity.has(t.data.path)&&this.showFileDetails(t.data.path)}showFileDetails(e){const t=this.fileActivity.get(e);if(!t)return;const i=document.getElementById("module-data-content");if(!i)return;const s=document.querySelector(".module-data-header h5");s&&(s.innerHTML=`📄 ${e.split("/").pop()}`);let n='<div style="padding: 10px; overflow-y: auto; height: 100%;">';n+='<div style="margin-bottom: 15px;">',n+=`<strong>File Path:</strong> ${e}<br>`,n+=`<strong>Operations:</strong> ${t.operations.length}<br>`,n+=`<strong>Sessions:</strong> ${t.sessions.size}`,n+="</div>",n+='<div style="margin-bottom: 15px;"><strong>Operations Timeline:</strong></div>',t.operations.forEach((e,t)=>{const i=new Date(e.timestamp).toLocaleTimeString();n+=`<div style="margin-bottom: 10px; padding: 8px; background: #f5f5f5; border-left: 3px solid ${this.getOperationColor(e.type)};">`,n+=`<div><strong>${e.type}</strong> at ${i}</div>`,"Edit"===e.type&&e.parameters&&(n+='<div style="margin-top: 5px; font-size: 0.9em;">',n+=`<div style="color: #d32f2f;">- ${this.escapeHtml(e.parameters.old_string||"").substring(0,100)}</div>`,n+=`<div style="color: #388e3c;">+ ${this.escapeHtml(e.parameters.new_string||"").substring(0,100)}</div>`,n+="</div>"),n+="</div>"}),t.astPaths.length>0&&(n+='<div style="margin-top: 15px;"><strong>AST Structure:</strong></div>',n+='<ul style="list-style: none; padding-left: 10px;">',t.astPaths.forEach(e=>{const t="class"===e.type?"🔷":"function"===e.type?"🔶":"🔸";n+=`<li>${t} ${e.name} (${e.type})</li>`}),n+="</ul>"),n+="</div>",i.innerHTML=n}getOperationColor(e){switch(e){case"Write":return"#4CAF50";case"Edit":return"#FF9800";case"Read":return"#2196F3";default:return"#999"}}escapeHtml(e){const t=document.createElement("div");return t.textContent=e,t.innerHTML}expandAllNodes(){this.d3Root&&(this.d3Root.descendants().forEach(e=>{e._children&&(e.children=e._children,e._children=null)}),this.renderTree())}collapseAllNodes(){this.d3Root&&(this.d3Root.descendants().forEach(e=>{e.children&&e.depth>0&&(e._children=e.children,e.children=null)}),this.renderTree())}resetZoom(){this.d3Tree&&this.d3Tree.svg.transition().duration(750).call(this.d3Tree.zoom.transform,d3.zoomIdentity)}updateSessionList(){const e=document.getElementById("session-select");if(!e)return;const t=e.value;for(;e.options.length>1;)e.remove(1);for(const[i,s]of this.sessions.entries()){let t=!1;for(let s=0;s<e.options.length;s++)if(e.options[s].value===i){t=!0;break}if(!t){const t=document.createElement("option");t.value=i,t.textContent=`Session ${i.substring(0,8)}... (${s.files.size} files)`,e.appendChild(t)}}t&&(e.value=t)}updateStats(){const e=document.getElementById("claude-tree-stats");if(!e)return;const t=this.currentSession?Array.from(this.fileActivity.values()).filter(e=>e.sessions.has(this.currentSession)).length:this.fileActivity.size,i=this.currentSession?Array.from(this.fileActivity.values()).filter(e=>e.sessions.has(this.currentSession)).reduce((e,t)=>e+t.operations.length,0):Array.from(this.fileActivity.values()).reduce((e,t)=>e+t.operations.length,0);e.textContent=`Files: ${t} | Operations: ${i} | Sessions: ${this.sessions.size}`}refreshFromFileToolTracker(){if(!window.dashboard||!window.dashboard.fileToolTracker)return void console.log("[CodeViewer] FileToolTracker not available");const e=window.dashboard.fileToolTracker.getFileOperations();console.log("[CodeViewer] Refreshing from FileToolTracker:",e.size,"files"),this.fileActivity.clear(),this.sessions.clear();const t="current-session";this.sessions.set(t,{id:t,startTime:(new Date).toISOString(),files:new Set}),this.currentSession=t,e.forEach((e,i)=>{this.sessions.get(t).files.add(i);const s=e.operations[0];e.operations[e.operations.length-1],this.fileActivity.set(i,{path:i,firstAccess:s?s.timestamp:e.lastOperation,lastAccess:e.lastOperation,accessCount:e.operations.length,operations:e.operations.map(e=>({type:e.operation,timestamp:e.timestamp,agent:e.agent})),workingDirectory:s?s.workingDirectory:null,astNodes:[],content:null})}),console.log("[CodeViewer] File activity refreshed:",this.fileActivity.size,"files")}}try{window.CodeViewer=new e,console.log("[CodeViewer] Instance created successfully")}catch(t){console.error("[CodeViewer] FAILED TO CREATE INSTANCE:",t)}if("loading"===document.readyState)document.addEventListener("DOMContentLoaded",()=>{console.log("[CodeViewer] DOMContentLoaded - attempting initialization");try{window.CodeViewer.initialize();const e=document.getElementById("claude-tree-tab");e&&e.classList.contains("active")&&setTimeout(()=>window.CodeViewer.show(),100)}catch(t){console.error("[CodeViewer] FAILED TO INITIALIZE:",t)}});else{console.log("[CodeViewer] DOM already loaded - initializing immediately");try{window.CodeViewer.initialize();const e=document.getElementById("claude-tree-tab");e&&e.classList.contains("active")&&(console.log("[CodeViewer] File Tree tab is active, showing in 100ms"),setTimeout(()=>window.CodeViewer.show(),100))}catch(t){console.error("[CodeViewer] FAILED TO INITIALIZE:",t)}}document.addEventListener("tabChanged",e=>{e.detail&&"claude-tree"===e.detail.newTab&&setTimeout(()=>window.CodeViewer.show(),50)}),setInterval(()=>{const e=document.getElementById("claude-tree-tab"),t=document.getElementById("claude-tree-container");e&&e.classList.contains("active")&&t&&!t.querySelector(".activity-tree-wrapper")&&!t.querySelector(".file-tree-empty-state")&&window.CodeViewer.show()},5e3);
2
- //# sourceMappingURL=code-viewer.js.map
@@ -1,2 +0,0 @@
1
- import{E as e,E as r}from"./event-viewer.js";export{e as EventProcessor,r as default};
2
- //# sourceMappingURL=event-processor.js.map
@@ -1,2 +0,0 @@
1
- window.EventViewer=class{constructor(e,t){this.container=document.getElementById(e),this.socketClient=t,this.events=[],this.filteredEvents=[],this.selectedEventIndex=-1,this.filteredEventElements=[],this.autoScroll=!0,this.searchFilter="",this.typeFilter="",this.sessionFilter="",this.eventTypeCount={},this.availableEventTypes=new Set,this.errorCount=0,this.eventsThisMinute=0,this.lastMinute=(new Date).getMinutes(),this.init()}init(){this.setupEventHandlers(),this.setupKeyboardNavigation(),this.socketClient.onEventUpdate((e,t)=>{this.events=Array.isArray(e)?e:[],this.updateDisplay()})}setupEventHandlers(){const e=document.getElementById("events-search-input");e&&e.addEventListener("input",e=>{this.searchFilter=e.target.value.toLowerCase(),this.applyFilters()});const t=document.getElementById("events-type-filter");t&&t.addEventListener("change",e=>{this.typeFilter=e.target.value,this.applyFilters()})}setupKeyboardNavigation(){}handleArrowNavigation(e){if(0===this.filteredEventElements.length)return;let t=this.selectedEventIndex+e;t>=this.filteredEventElements.length?t=0:t<0&&(t=this.filteredEventElements.length-1),this.showEventDetails(t)}applyFilters(){this.events&&Array.isArray(this.events)||(console.warn("EventViewer: events array is not initialized, using empty array"),this.events=[]),this.filteredEvents=this.events.filter(e=>{if(this.searchFilter){if(![e.type||"",e.subtype||"",JSON.stringify(e.data||{})].join(" ").toLowerCase().includes(this.searchFilter))return!1}if(this.typeFilter){const t=e.type&&""!==e.type.trim()?e.type:"";if((e.subtype&&t?`${t}.${e.subtype}`:t)!==this.typeFilter)return!1}return!(this.sessionFilter&&""!==this.sessionFilter&&(!e.data||e.data.session_id!==this.sessionFilter))}),this.renderEvents(),this.updateMetrics()}updateEventTypeDropdown(){const e=document.getElementById("events-type-filter");if(!e)return;const t=new Set;this.events&&Array.isArray(this.events)||(console.warn("EventViewer: events array is not initialized in updateEventTypeDropdown"),this.events=[]),this.events.forEach(e=>{if(e.type&&""!==e.type.trim()){const n=e.subtype?`${e.type}.${e.subtype}`:e.type;t.add(n)}});const n=Array.from(t).sort(),s=Array.from(this.availableEventTypes).sort();if(JSON.stringify(n)===JSON.stringify(s))return;this.availableEventTypes=t;const o=e.value;e.innerHTML='<option value="">All Events</option>';Array.from(t).sort().forEach(t=>{const n=document.createElement("option");n.value=t,n.textContent=t,e.appendChild(n)}),o&&t.has(o)?e.value=o:o&&!t.has(o)&&(e.value="",this.typeFilter="")}updateDisplay(){this.updateEventTypeDropdown(),this.applyFilters()}renderEvents(){const e=this.container;if(!e)return void console.warn("[EventViewer] Container not found, skipping render");if("events-list"!==e.id)return void console.error("[EventViewer] CRITICAL: Attempting to render to wrong container:",e.id);const t=e.closest(".tab-content");if(!t||"events-tab"!==t.id)return void console.error("[EventViewer] CRITICAL: events-list is not inside events-tab!");const n=document.getElementById("events-tab");if(!n||!n.classList.contains("active"))return void console.log("[EventViewer] Events tab not active, skipping render");const s=document.getElementById("claude-tree-tab");if(s&&s.classList.contains("active"))return void console.error("[EventViewer] CRITICAL: File Tree tab is active, blocking event render!");const o=e.scrollTop+e.clientHeight>=e.scrollHeight-10;if(0===this.filteredEvents.length)return e.innerHTML=`\n <div class="no-events">\n ${0===this.events.length?"Connect to Socket.IO server to see events...":"No events match current filters..."}\n </div>\n `,void(this.filteredEventElements=[]);const i=this.filteredEvents.map((e,t)=>{const n=new Date(e.timestamp).toLocaleTimeString();return`\n <div class="event-item single-row ${e.type?`event-${e.type}`:"event-default"} ${t===this.selectedEventIndex?"selected":""}"\n onclick="eventViewer.showEventDetails(${t})"\n data-index="${t}">\n <span class="event-single-row-content">\n <span class="event-content-main">${this.formatSingleRowEventContent(e)}</span>\n <span class="event-timestamp">${n}</span>\n </span>\n ${this.createInlineEditDiffViewer(e,t)}\n </div>\n `}).join("");e.innerHTML=i,this.filteredEventElements=Array.from(e.querySelectorAll(".event-item")),window.dashboard&&"events"===window.dashboard.currentTab&&window.dashboard.tabNavigation&&window.dashboard.tabNavigation.events&&(window.dashboard.tabNavigation.events.items=this.filteredEventElements),this.filteredEvents.length>0&&o&&this.autoScroll&&requestAnimationFrame(()=>{e.scrollTop=e.scrollHeight})}formatEventType(e){return e.type&&e.subtype?e.type===e.subtype||"generic"===e.subtype?e.type:`${e.type}.${e.subtype}`:e.type?e.type:e.originalEventName?e.originalEventName:"unknown"}formatEventData(e){if(!e.data)return"No data";switch(e.type){case"session":return this.formatSessionEvent(e);case"claude":return this.formatClaudeEvent(e);case"agent":return this.formatAgentEvent(e);case"hook":return this.formatHookEvent(e);case"todo":return this.formatTodoEvent(e);case"memory":return this.formatMemoryEvent(e);case"log":return this.formatLogEvent(e);case"code":return this.formatCodeEvent(e);default:return this.formatGenericEvent(e)}}formatSessionEvent(e){const t=e.data;return"started"===e.subtype?`<strong>Session started:</strong> ${t.session_id||"Unknown"}`:"ended"===e.subtype?`<strong>Session ended:</strong> ${t.session_id||"Unknown"}`:`<strong>Session:</strong> ${JSON.stringify(t)}`}formatClaudeEvent(e){const t=e.data;if("request"===e.subtype){const e=t.prompt||t.message||"";return`<strong>Request:</strong> ${e.length>100?e.substring(0,100)+"...":e}`}if("response"===e.subtype){const e=t.response||t.content||"";return`<strong>Response:</strong> ${e.length>100?e.substring(0,100)+"...":e}`}return`<strong>Claude:</strong> ${JSON.stringify(t)}`}formatAgentEvent(e){const t=e.data;return"loaded"===e.subtype?`<strong>Agent loaded:</strong> ${t.agent_type||t.name||"Unknown"}`:"executed"===e.subtype?`<strong>Agent executed:</strong> ${t.agent_type||t.name||"Unknown"}`:`<strong>Agent:</strong> ${JSON.stringify(t)}`}formatHookEvent(e){const t=e.data,n=t.event_type||e.subtype||"unknown";switch(n){case"user_prompt":const s=t.prompt_text||t.prompt_preview||"";return`<strong>User Prompt:</strong> ${(s.length>80?s.substring(0,80)+"...":s)||"No prompt text"}`;case"pre_tool":const o=t.tool_name||"Unknown tool";return`<strong>Pre-Tool (${t.operation_type||"operation"}):</strong> ${o}`;case"post_tool":const i=t.tool_name||"Unknown tool";return`<strong>Post-Tool (${t.success?"success":t.status||"failed"}):</strong> ${i}${t.duration_ms?` (${t.duration_ms}ms)`:""}`;case"notification":return`<strong>Notification (${t.notification_type||"notification"}):</strong> ${t.message_preview||t.message||"No message"}`;case"stop":const r=t.reason||"unknown";return`<strong>Stop (${t.stop_type||"normal"}):</strong> ${r}`;case"subagent_start":const a=t.agent_type||t.agent||t.subagent_type||"Unknown",l=t.prompt||t.description||t.task||"No description",d=l.length>60?l.substring(0,60)+"...":l;return`<strong>Subagent Start (${this.formatAgentType(a)}):</strong> ${d}`;case"subagent_stop":const c=t.agent_type||t.agent||t.subagent_type||"Unknown",p=t.reason||t.stop_reason||"completed",g=this.formatAgentType(c),u=t.structured_response?.task_completed;return`<strong>Subagent Stop (${g})${void 0!==u?u?" ✓":" ✗":""}:</strong> ${p}`;default:const h=t.hook_name||t.name||t.event_type||"Unknown";return`<strong>Hook ${e.subtype||n}:</strong> ${h}`}}formatTodoEvent(e){const t=e.data;if(t.todos&&Array.isArray(t.todos)){const e=t.todos.length;return`<strong>Todo updated:</strong> ${e} item${1!==e?"s":""}`}return`<strong>Todo:</strong> ${JSON.stringify(t)}`}formatMemoryEvent(e){const t=e.data;return`<strong>Memory ${t.operation||"unknown"}:</strong> ${t.key||"Unknown key"}`}formatLogEvent(e){const t=e.data,n=t.level||"info",s=t.message||"",o=s.length>80?s.substring(0,80)+"...":s;return`<strong>[${n.toUpperCase()}]</strong> ${o}`}formatCodeEvent(e){const t=e.data||{};if("progress"===e.subtype){const e=t.message||"Processing...",n=t.percentage;return void 0!==n?`<strong>Progress:</strong> ${e} (${Math.round(n)}%)`:`<strong>Progress:</strong> ${e}`}if("analysis:queued"===e.subtype)return`<strong>Queued:</strong> Analysis for ${t.path||"Unknown path"}`;if("analysis:start"===e.subtype)return`<strong>Started:</strong> Analyzing ${t.path||"Unknown path"}`;if("analysis:complete"===e.subtype){return`<strong>Complete:</strong> Analysis finished${t.duration?` (${t.duration.toFixed(2)}s)`:""}`}if("analysis:error"===e.subtype)return`<strong>Error:</strong> ${t.message||"Analysis failed"}`;if("analysis:cancelled"===e.subtype)return`<strong>Cancelled:</strong> Analysis stopped for ${t.path||"Unknown path"}`;if("file:start"===e.subtype)return`<strong>File:</strong> Processing ${t.file||"Unknown file"}`;if("file:complete"===e.subtype){const e=void 0!==t.nodes_count?` (${t.nodes_count} nodes)`:"";return`<strong>File done:</strong> ${t.file||"Unknown file"}${e}`}if("node:found"===e.subtype)return`<strong>Node:</strong> Found ${t.node_type||"element"} "${t.name||"unnamed"}"`;if("error"===e.subtype)return`<strong>Error:</strong> ${t.error||"Unknown error"} in ${t.file||"file"}`;const n=JSON.stringify(t);return`<strong>Code:</strong> ${n.length>100?n.substring(0,100)+"...":n}`}formatGenericEvent(e){const t=e.data;return"string"==typeof t?t.length>100?t.substring(0,100)+"...":t:JSON.stringify(t)}formatAgentType(e){const t={research:"Research",architect:"Architect",engineer:"Engineer",qa:"QA",pm:"PM",project_manager:"PM",research_agent:"Research",architect_agent:"Architect",engineer_agent:"Engineer",qa_agent:"QA",unknown:"Unknown"},n=(e||"unknown").toLowerCase();if(t[n])return t[n];const s=e.match(/^(\w+)(?:_agent|Agent)?$/i);return s&&s[1]?s[1].charAt(0).toUpperCase()+s[1].slice(1).toLowerCase():e.charAt(0).toUpperCase()+e.slice(1)}formatSingleRowEventContent(e){const t=this.formatEventType(e),n=e.data||{},s=e.source&&"system"!==e.source?`[${e.source}] `:"";let o="";switch(e.type){case"hook":const t=e.tool_name||n.tool_name||"Unknown",s=e.subtype||"Unknown";if("pre_tool"===s||"post_tool"===s){const e=n.operation_type||"",i="post_tool"===s&&void 0!==n.success?n.success?"✓":"✗":"";o=`${t}${e?` (${e})`:""}${i?` ${i}`:""}`}else if("user_prompt"===s){const e=n.prompt_text||n.prompt_preview||"";o=(e.length>60?e.substring(0,60)+"...":e)||"No prompt text"}else if("subagent_start"===s){const e=n.agent_type||n.agent||n.subagent_type||"Unknown",t=this.formatAgentType(e),s=n.prompt||n.description||n.task||"",i=s.length>40?s.substring(0,40)+"...":s;o=i?`${t} - ${i}`:t}else if("subagent_stop"===s){const e=n.agent_type||n.agent||n.subagent_type||"Unknown",t=this.formatAgentType(e),s=n.reason||n.stop_reason||"completed",i=n.structured_response?.task_completed,r=void 0!==i?i?"✓":"✗":"";o=`${t}${r?" "+r:""} - ${s}`}else if("stop"===s){const e=n.reason||"completed";o=`${n.stop_type||"normal"} - ${e}`}else o=t;break;case"agent":const i=e.subagent_type||n.subagent_type||"PM",r=n.status||"";o=`${i}${r?` - ${r}`:""}`;break;case"todo":if(n.todos&&Array.isArray(n.todos)){o=`${n.todos.length} items (${n.todos.filter(e=>"completed"===e.status).length} completed, ${n.todos.filter(e=>"in_progress"===e.status).length} in progress)`}else o="Todo update";break;case"memory":o=`${n.operation||"unknown"}: ${n.key||"unknown"}${n.value?` = ${JSON.stringify(n.value).substring(0,30)}...`:""}`;break;case"session":o=`ID: ${n.session_id||"unknown"}`;break;case"claude":if("request"===e.subtype){const e=n.prompt||n.message||"";o=(e.length>60?e.substring(0,60)+"...":e)||"Empty request"}else if("response"===e.subtype){const e=n.response||n.content||"";o=(e.length>60?e.substring(0,60)+"...":e)||"Empty response"}else o=n.message||"Claude interaction";break;case"log":const a=n.level||"info",l=n.message||"",d=l.length>60?l.substring(0,60)+"...":l;o=`[${a.toUpperCase()}] ${d}`;break;case"test":o=n.test_name||n.name||"Test";break;default:if("string"==typeof n)o=n.length>60?n.substring(0,60)+"...":n;else if(n.message)o=n.message.length>60?n.message.substring(0,60)+"...":n.message;else if(n.name)o=n.name;else if(Object.keys(n).length>0){const e=Object.keys(n).find(e=>!["timestamp","id"].includes(e));if(e){const t=n[e];o=`${e}: ${"object"==typeof t?JSON.stringify(t).substring(0,40)+"...":t}`}}}const i=`${s}${t}`;return o?`${i} - ${o}`:i}getHookDisplayName(e,t){const n={pre_tool:"Pre-Tool",post_tool:"Post-Tool",user_prompt:"User-Prompt",stop:"Stop",subagent_start:"Subagent-Start",subagent_stop:"Subagent-Stop",notification:"Notification"};if(n[e])return n[e];return String(e||"unknown").replace(/_/g," ")}getEventCategory(e){const t=e.data||{},n=e.tool_name||t.tool_name||"";return["Read","Write","Edit","MultiEdit"].includes(n)?"file_operations":["Bash","grep","Glob"].includes(n)?"system_operations":"TodoWrite"===n?"task_management":"Task"===n||"subagent_start"===e.subtype||"subagent_stop"===e.subtype?"agent_delegation":"stop"===e.subtype?"session_control":"general"}showEventDetails(e){if(!this.filteredEvents||!Array.isArray(this.filteredEvents))return void console.warn("EventViewer: filteredEvents array is not initialized");if(e<0||e>=this.filteredEvents.length)return;this.selectedEventIndex=e;const t=this.filteredEvents[e];window.dashboard&&(window.dashboard.tabNavigation&&window.dashboard.tabNavigation.events&&(window.dashboard.tabNavigation.events.selectedIndex=e),window.dashboard.selectCard&&window.dashboard.selectCard("events",e,"event",t)),this.filteredEventElements.forEach((t,n)=>{t.classList.toggle("selected",n===e)}),document.dispatchEvent(new CustomEvent("eventSelected",{detail:{event:t,index:e}}));const n=this.filteredEventElements[e];n&&n.scrollIntoView({behavior:"smooth",block:"nearest"})}clearSelection(){this.selectedEventIndex=-1,this.filteredEventElements.forEach(e=>{e.classList.remove("selected")}),window.dashboard&&(window.dashboard.tabNavigation&&window.dashboard.tabNavigation.events&&(window.dashboard.tabNavigation.events.selectedIndex=-1),window.dashboard.clearCardSelection&&window.dashboard.clearCardSelection()),document.dispatchEvent(new CustomEvent("eventSelectionCleared"))}updateMetrics(){this.eventTypeCount={},this.errorCount=0,this.events&&Array.isArray(this.events)||(console.warn("EventViewer: events array is not initialized in updateMetrics"),this.events=[]),this.events.forEach(e=>{const t=e.type||"unknown";this.eventTypeCount[t]=(this.eventTypeCount[t]||0)+1,"log"===e.type&&e.data&&["error","critical"].includes(e.data.level)&&this.errorCount++});const e=(new Date).getMinutes();e!==this.lastMinute&&(this.lastMinute=e,this.eventsThisMinute=0);const t=new Date(Date.now()-6e4);this.eventsThisMinute=this.events.filter(e=>new Date(e.timestamp)>t).length,this.updateMetricsUI()}updateMetricsUI(){const e=document.getElementById("total-events"),t=document.getElementById("events-per-minute"),n=document.getElementById("unique-types"),s=document.getElementById("error-count");e&&(e.textContent=this.events.length),t&&(t.textContent=this.eventsThisMinute),n&&(n.textContent=Object.keys(this.eventTypeCount).length),s&&(s.textContent=this.errorCount)}exportEvents(){const e=JSON.stringify(this.filteredEvents,null,2),t=new Blob([e],{type:"application/json"}),n=URL.createObjectURL(t),s=document.createElement("a");s.href=n,s.download=`claude-mpm-events-${(new Date).toISOString().split("T")[0]}.json`,s.click(),URL.revokeObjectURL(n)}clearEvents(){this.socketClient.clearEvents(),this.selectedEventIndex=-1,this.updateDisplay()}setSessionFilter(e){this.sessionFilter=e,this.applyFilters()}getFilters(){return{search:this.searchFilter,type:this.typeFilter,session:this.sessionFilter}}getFilteredEvents(){return this.filteredEvents}getAllEvents(){return this.events}createInlineEditDiffViewer(e,t){const n=e.data||{},s=e.tool_name||n.tool_name||"";if(!["Edit","MultiEdit"].includes(s))return"";let o=[];if("Edit"===s){const t=e.tool_parameters||n.tool_parameters||{};t.old_string&&t.new_string&&o.push({old_string:t.old_string,new_string:t.new_string,file_path:t.file_path||"unknown"})}else if("MultiEdit"===s){const t=e.tool_parameters||n.tool_parameters||{};t.edits&&Array.isArray(t.edits)&&(o=t.edits.map(e=>({...e,file_path:t.file_path||"unknown"})))}if(0===o.length)return"";const i=`edit-diff-${t}`,r=o.length>1;let a="";return o.forEach((e,t)=>{const n=this.createDiffHtml(e.old_string,e.new_string);a+=`\n <div class="edit-diff-section">\n ${r?`<div class="edit-diff-header">Edit ${t+1}</div>`:""}\n <div class="diff-content">${n}</div>\n </div>\n `}),`\n <div class="inline-edit-diff-viewer">\n <div class="diff-toggle-header" onclick="eventViewer.toggleEditDiff('${i}', event)">\n <span class="diff-toggle-icon">📋</span>\n <span class="diff-toggle-text">Show ${r?o.length+" edits":"edit"}</span>\n <span class="diff-toggle-arrow">▼</span>\n </div>\n <div id="${i}" class="diff-content-container" style="display: none;">\n ${a}\n </div>\n </div>\n `}createDiffHtml(e,t){const n=e.split("\n"),s=t.split("\n");let o="",i=0,r=0;for(;i<n.length||r<s.length;){const e=i<n.length?n[i]:null,t=r<s.length?s[r]:null;null===e?(o+=`<div class="diff-line diff-added">+ ${this.escapeHtml(t)}</div>`,r++):null===t?(o+=`<div class="diff-line diff-removed">- ${this.escapeHtml(e)}</div>`,i++):e===t?(o+=`<div class="diff-line diff-unchanged"> ${this.escapeHtml(e)}</div>`,i++,r++):(o+=`<div class="diff-line diff-removed">- ${this.escapeHtml(e)}</div>`,o+=`<div class="diff-line diff-added">+ ${this.escapeHtml(t)}</div>`,i++,r++)}return`<div class="diff-container">${o}</div>`}toggleEditDiff(e,t){t.stopPropagation();const n=document.getElementById(e),s=t.currentTarget.querySelector(".diff-toggle-arrow");if(n){const e="none"!==n.style.display;n.style.display=e?"none":"block",s&&(s.textContent=e?"▼":"▲")}}escapeHtml(e){const t=document.createElement("div");return t.textContent=e,t.innerHTML}};class e{constructor(e,t){this.eventViewer=e,this.agentInference=t,this.agentEvents=[],this.filteredAgentEvents=[],this.filteredToolEvents=[],this.filteredFileEvents=[],this.selectedSessionId=null,console.log("Event processor initialized")}getFilteredEventsForTab(e){const t=this.eventViewer.events;console.log(`getFilteredEventsForTab(${e}) - using RAW events: ${t.length} total`);const n=window.sessionManager;if(n&&n.selectedSessionId){const e=n.getEventsForSession(n.selectedSessionId);return console.log(`Filtering by session ${n.selectedSessionId}: ${e.length} events`),e}return t}applyAgentsFilters(e){const t=document.getElementById("agents-search-input"),n=document.getElementById("agents-type-filter"),s=t?t.value.toLowerCase():"",o=n?n.value:"";return e.filter(e=>{if(s){if(![e.agentName||"",e.type||"",e.isImplied?"implied":"explicit"].join(" ").toLowerCase().includes(s))return!1}if(o){if(!(e.agentName||"unknown").toLowerCase().includes(o.toLowerCase()))return!1}return!0})}applyToolsFilters(e){const t=document.getElementById("tools-search-input"),n=document.getElementById("tools-type-filter"),s=t?t.value.toLowerCase():"",o=n?n.value:"";return e.filter(e=>{if(s){if(![e.tool_name||"",e.agent_type||"",e.type||"",e.subtype||""].join(" ").toLowerCase().includes(s))return!1}if(o){if((e.tool_name||"")!==o)return!1}return!0})}applyToolCallFilters(e){const t=document.getElementById("tools-search-input"),n=document.getElementById("tools-type-filter"),s=t?t.value.toLowerCase():"",o=n?n.value:"";return e.filter(([e,t])=>{if(s){if(![t.tool_name||"",t.agent_type||"","tool_call"].join(" ").toLowerCase().includes(s))return!1}if(o){if((t.tool_name||"")!==o)return!1}return!0})}applyFilesFilters(e){const t=document.getElementById("files-search-input"),n=document.getElementById("files-type-filter"),s=t?t.value.toLowerCase():"",o=n?n.value:"";return e.filter(([e,t])=>{if(this.selectedSessionId){const e=t.operations.filter(e=>e.sessionId===this.selectedSessionId);if(0===e.length)return!1;t={...t,operations:e,lastOperation:e[e.length-1]?.timestamp||t.lastOperation}}if(s){if(![e,...t.operations.map(e=>e.operation),...t.operations.map(e=>e.agent)].join(" ").toLowerCase().includes(s))return!1}if(o){if(!t.operations.map(e=>e.operation).includes(o))return!1}return!0})}extractOperation(e){if(!e)return"unknown";const t=e.toLowerCase();return t.includes("read")?"read":t.includes("write")?"write":t.includes("edit")?"edit":t.includes("create")?"create":t.includes("delete")?"delete":t.includes("move")||t.includes("rename")?"move":"other"}extractToolFromHook(e){if(!e)return"";const t=e.match(/^(?:Pre|Post)(.+)Use$/);return t?t[1]:""}extractToolFromSubtype(e){if(!e)return"";if(e.includes("_")){return e.split("_")[0]||""}return e}extractToolTarget(e,t,n){const s=t||n||{};switch(e?.toLowerCase()){case"read":case"write":case"edit":return s.file_path||s.path||"";case"bash":return s.command||"";case"grep":return s.pattern||"";case"task":return s.subagent_type||s.agent_type||"";default:const e=Object.keys(s),t=["path","file_path","command","pattern","query","target"];for(const n of t)if(s[n])return s[n];return e.length>0?`${e[0]}: ${s[e[0]]}`:""}}generateAgentHTML(e){const t=this.agentInference.getUniqueAgentInstances();return this.applyAgentsFilters(t).map((e,t)=>{const n=e.agentName,s=this.formatTimestamp(e.firstTimestamp||e.timestamp),o=e.isImplied?"implied":"explicit",i=e.totalEventCount||e.eventCount||0;return`\n <div class="event-item single-row event-agent" onclick="${`dashboard.selectCard('agents', ${t}, 'agent_instance', '${e.id}'); dashboard.showAgentInstanceDetails('${e.id}');`}">\n <span class="event-single-row-content">\n <span class="event-content-main">${`${n} (${o}, ${i} events)`}</span>\n <span class="event-timestamp">${s}</span>\n </span>\n </div>\n `}).join("")}generateToolHTML(e){return this.applyToolCallFilters(e).map(([e,t],n)=>{const s=t.tool_name||"Unknown",o=t.agent_type||"Unknown",i=this.formatTimestamp(t.timestamp);return`\n <div class="event-item single-row event-tool ${"completed"===(t.post_event?"completed":"pending")?"status-success":"status-pending"}" onclick="dashboard.selectCard('tools', ${n}, 'toolCall', '${e}'); dashboard.showToolCallDetails('${e}')">\n <span class="event-single-row-content">\n <span class="event-content-main">${`${s} (${"pm"===o.toLowerCase()?"pm":o})`}</span>\n <span class="event-timestamp">${i}</span>\n </span>\n </div>\n `}).join("")}generateFileHTML(e){return this.applyFilesFilters(e).map(([e,t],n)=>{const s=t.operations.map(e=>e.operation),o=this.formatTimestamp(t.lastOperation),i={};s.forEach(e=>{i[e]=(i[e]||0)+1});const r=Object.entries(i).map(([e,t])=>`${e}(${t})`).join(", "),a=[...new Set(t.operations.map(e=>e.agent))],l=a.length>1?`by ${a.length} agents`:`by ${a[0]||"unknown"}`;return`\n <div class="event-item single-row file-item" onclick="dashboard.selectCard('files', ${n}, 'file', '${e}'); dashboard.showFileDetails('${e}')">\n <span class="event-single-row-content">\n <span class="event-content-main">${`${this.getRelativeFilePath(e)} ${r} ${l}`}</span>\n <span class="event-timestamp">${o}</span>\n </span>\n </div>\n `}).join("")}getFileOperationIcon(e){return e.includes("write")||e.includes("create")?"📝":e.includes("edit")?"✏️":e.includes("read")?"👁️":e.includes("delete")?"🗑️":e.includes("move")?"📦":"📄"}getRelativeFilePath(e){if(!e)return"";const t=e.split("/");return t.length>3?".../"+t.slice(-2).join("/"):e}formatTimestamp(e){if(!e)return"";return new Date(e).toLocaleTimeString()}setSelectedSessionId(e){this.selectedSessionId=e}getSelectedSessionId(){return this.selectedSessionId}getUniqueToolInstances(e){return this.applyToolCallFilters(e)}getUniqueFileInstances(e){return this.applyFilesFilters(e)}showAgentInstanceDetails(e){const t=this.agentInference.getPMDelegations().get(e);if(!t)return void console.error("Agent instance not found:",e);console.log("Showing agent instance details for:",e,t);const n=`\n <div class="agent-instance-details">\n <h3>Agent Instance: ${t.agentName}</h3>\n <p><strong>Type:</strong> ${t.isImplied?"Implied PM Delegation":"Explicit PM Delegation"}</p>\n <p><strong>Start Time:</strong> ${this.formatTimestamp(t.timestamp)}</p>\n <p><strong>Event Count:</strong> ${t.agentEvents.length}</p>\n <p><strong>Session:</strong> ${t.sessionId}</p>\n ${t.pmCall?`<p><strong>PM Call:</strong> Task delegation to ${t.agentName}</p>`:"<p><strong>Note:</strong> Implied delegation (no explicit PM call found)</p>"}\n </div>\n `;console.log("Agent instance details HTML:",n)}}window.EventProcessor=e;export{e as E};
2
- //# sourceMappingURL=event-viewer.js.map
@@ -1,2 +0,0 @@
1
- window.ExportManager=class{constructor(e){this.eventViewer=e,this.setupEventHandlers(),console.log("Export manager initialized")}setupEventHandlers(){const e=document.querySelector('button[onclick="clearEvents()"]'),t=document.getElementById("export-btn");e&&e.addEventListener("click",()=>{this.clearEvents()}),t&&t.addEventListener("click",()=>{this.exportEvents()})}exportEvents(){this.eventViewer?this.eventViewer.exportEvents():console.error("Cannot export events: EventViewer not available")}clearEvents(){document.dispatchEvent(new CustomEvent("eventsClearing")),this.eventViewer&&this.eventViewer.clearEvents(),document.dispatchEvent(new CustomEvent("eventsCleared")),console.log("Events cleared")}exportEventsCustom(e={}){const{format:t="json",events:n=null,filename:o=null}=e,r=n||(this.eventViewer?this.eventViewer.events:[]);if(0===r.length)return void console.warn("No events to export");const i=(new Date).toISOString().replace(/[:.]/g,"-"),s=o||`claude-mpm-events-${i}`;let l="",a="",c="";switch(t.toLowerCase()){case"json":l=JSON.stringify(r,null,2),a="application/json",c=".json";break;case"csv":l=this.convertEventsToCSV(r),a="text/csv",c=".csv";break;case"txt":l=this.convertEventsToText(r),a="text/plain",c=".txt";break;default:return void console.error("Unsupported export format:",t)}this.downloadFile(l,s+c,a)}convertEventsToCSV(e){if(0===e.length)return"";return[["timestamp","type","subtype","tool_name","agent_type","session_id","data"],...e.map(e=>[e.timestamp||"",e.type||"",e.subtype||"",e.tool_name||"",e.agent_type||"",e.session_id||"",JSON.stringify(e.data||{}).replace(/"/g,'""')])].map(e=>e.map(e=>`"${e}"`).join(",")).join("\n")}convertEventsToText(e){return 0===e.length?"No events to export.":e.map((e,t)=>{const n=this.formatTimestamp(e.timestamp);let o=`Event ${t+1}: ${e.type||"Unknown"}${e.subtype?` (${e.subtype})`:""}${e.tool_name?` - Tool: ${e.tool_name}`:""}${e.agent_type?` - Agent: ${e.agent_type}`:""}\n`;return o+=` Time: ${n}\n`,o+=` Session: ${e.session_id||"Unknown"}\n`,e.data&&Object.keys(e.data).length>0&&(o+=` Data: ${JSON.stringify(e.data,null,2)}\n`),o}).join("\n"+"=".repeat(80)+"\n")}downloadFile(e,t,n){try{const o=new Blob([e],{type:n}),r=window.URL.createObjectURL(o),i=document.createElement("a");i.href=r,i.download=t,i.style.display="none",document.body.appendChild(i),i.click(),document.body.removeChild(i),window.URL.revokeObjectURL(r),console.log(`File exported: ${t}`)}catch(o){console.error("Failed to export file:",o)}}formatTimestamp(e){if(!e)return"Unknown time";try{const t=new Date(e);return isNaN(t.getTime())?"Invalid time":t.toLocaleTimeString("en-US",{hour12:!1,hour:"2-digit",minute:"2-digit",second:"2-digit"})}catch(t){return console.error("Error formatting timestamp:",t),"Error formatting time"}}formatFullTimestamp(e){if(!e)return"Unknown time";try{const t=new Date(e);return isNaN(t.getTime())?"Invalid time":t.toLocaleString("en-US",{year:"numeric",month:"2-digit",day:"2-digit",hour:"2-digit",minute:"2-digit",second:"2-digit",hour12:!1})}catch(t){return console.error("Error formatting full timestamp:",t),"Error formatting time"}}scrollListToBottom(e){console.log(`[DEBUG] scrollListToBottom called with listId: ${e}`),setTimeout(()=>{const t=document.getElementById(e);console.log(`[DEBUG] Element found for ${e}:`,t),t?(console.log(`[DEBUG] Scrolling ${e} - scrollHeight: ${t.scrollHeight}, scrollTop before: ${t.scrollTop}`),t.scrollTop=t.scrollHeight,console.log(`[DEBUG] Scrolled ${e} - scrollTop after: ${t.scrollTop}`)):console.warn(`[DEBUG] Element with ID '${e}' not found for scrolling`)},50)}debounce(e,t){let n;return function(...o){clearTimeout(n),n=setTimeout(()=>{clearTimeout(n),e(...o)},t)}}throttle(e,t){let n;return function(...o){n||(e.apply(this,o),n=!0,setTimeout(()=>n=!1,t))}}generateId(){return Date.now().toString(36)+Math.random().toString(36).substr(2)}deepClone(e){if(null===e||"object"!=typeof e)return e;if(e instanceof Date)return new Date(e.getTime());if(e instanceof Array)return e.map(e=>this.deepClone(e));if("object"==typeof e){const t={};for(const n in e)e.hasOwnProperty(n)&&(t[n]=this.deepClone(e[n]));return t}return e}};
2
- //# sourceMappingURL=export-manager.js.map
@@ -1,2 +0,0 @@
1
- window.FileToolTracker=class{constructor(e,t){this.agentInference=e,this.workingDirectoryManager=t,this.fileOperations=new Map,this.toolCalls=new Map,console.log("File-tool tracker initialized")}updateFileOperations(e){this.fileOperations.clear(),console.log("updateFileOperations - processing",e.length,"events");const t=new Map;let o=0;e.forEach((e,a)=>{const s=this.isFileOperation(e);if(s&&o++,a<5&&console.log(`Event ${a}:`,{type:e.type,subtype:e.subtype,tool_name:e.tool_name,tool_parameters:e.tool_parameters,isFileOp:s}),s){const o=e.tool_name||e.data&&e.data.tool_name,a=e.session_id||e.data&&e.data.session_id||"unknown",s=`${a}_${o}_${Math.floor(new Date(e.timestamp).getTime()/1e3)}`;t.has(s)||t.set(s,{pre_event:null,post_event:null,tool_name:o,session_id:a});const n=t.get(s);"pre_tool"===e.subtype||"hook"===e.type&&e.subtype&&!e.subtype.includes("post")?n.pre_event=e:("post_tool"===e.subtype||e.subtype&&e.subtype.includes("post")||(n.pre_event=e),n.post_event=e)}}),console.log("updateFileOperations - found",o,"file operations in",t.size,"event pairs"),t.forEach((e,t)=>{const o=this.extractFilePathFromPair(e);if(o){console.log("File operation detected for:",o,"from pair:",t),this.fileOperations.has(o)||this.fileOperations.set(o,{path:o,operations:[],lastOperation:null});const a=this.fileOperations.get(o),s=this.getFileOperationFromPair(e),n=e.post_event?.timestamp||e.pre_event?.timestamp,r=this.extractAgentFromPair(e),i=this.workingDirectoryManager.extractWorkingDirectoryFromPair(e);a.operations.push({operation:s,timestamp:n,agent:r.name,confidence:r.confidence,sessionId:e.session_id,details:this.getFileOperationDetailsFromPair(e),workingDirectory:i}),a.lastOperation=n}else console.log("No file path found for pair:",t,e)}),console.log("updateFileOperations - final result:",this.fileOperations.size,"file operations"),this.fileOperations.size>0&&console.log("File operations map:",Array.from(this.fileOperations.entries()))}updateToolCalls(e){this.toolCalls.clear(),console.log("updateToolCalls - processing",e.length,"events");const t=[],o=[];let a=0;e.forEach((e,s)=>{const n=this.isToolOperation(e);n&&a++,s<5&&console.log(`Tool Event ${s}:`,{type:e.type,subtype:e.subtype,tool_name:e.tool_name,tool_parameters:e.tool_parameters,isToolOp:n}),n&&("pre_tool"===e.subtype||"hook"===e.type&&e.subtype&&!e.subtype.includes("post")?t.push(e):("post_tool"===e.subtype||e.subtype&&e.subtype.includes("post")||t.push(e),o.push(e)))}),console.log("updateToolCalls - found",a,"tool operations:",t.length,"pre_tool,",o.length,"post_tool");const s=new Map,n=new Set;t.forEach((e,t)=>{const a=e.tool_name||e.data&&e.data.tool_name,r=e.session_id||e.data&&e.data.session_id||"unknown",i=new Date(e.timestamp).getTime(),l=`${r}_${a}_${t}_${i}`,p={pre_event:e,post_event:null,tool_name:a,session_id:r,operation_type:e.operation_type||"tool_execution",timestamp:e.timestamp,duration_ms:null,success:null,exit_code:null,result_summary:null,agent_type:null,agent_confidence:null},c=this.extractAgentFromEvent(e);p.agent_type=c.name,p.agent_confidence=c.confidence;let _=-1,m=-1;if(o.forEach((t,o)=>{if(n.has(o))return;const s=t.tool_name||t.data&&t.data.tool_name,l=t.session_id||t.data&&t.data.session_id||"unknown";if(s!==a||l!==r)return;const p=new Date(t.timestamp).getTime(),c=Math.abs(p-i);let u=0;p>=i-1e3&&c<=3e5&&(u=1e3-c/1e3,this.compareToolParameters(e,t)&&(u+=500),e.working_directory&&t.working_directory&&e.working_directory===t.working_directory&&(u+=100)),u>m&&(m=u,_=o)}),_>=0&&m>0){const t=o[_];p.post_event=t,p.duration_ms=t.duration_ms,p.success=t.success,p.exit_code=t.exit_code,p.result_summary=t.result_summary,n.add(_),console.log(`Paired pre_tool ${a} at ${e.timestamp} with post_tool at ${t.timestamp} (score: ${m})`)}else console.log(`No matching post_tool found for ${a} at ${e.timestamp} (still running or orphaned)`);s.set(l,p)}),o.forEach((e,t)=>{if(n.has(t))return;const o=e.tool_name||e.data&&e.data.tool_name;console.log("Orphaned post_tool event found:",o,"at",e.timestamp);const a=e.session_id||e.data&&e.data.session_id||"unknown",r=`orphaned_${a}_${o}_${t}_${new Date(e.timestamp).getTime()}`,i={pre_event:null,post_event:e,tool_name:o,session_id:a,operation_type:"tool_execution",timestamp:e.timestamp,duration_ms:e.duration_ms,success:e.success,exit_code:e.exit_code,result_summary:e.result_summary,agent_type:null,agent_confidence:null},l=this.extractAgentFromEvent(e);i.agent_type=l.name,i.agent_confidence=l.confidence,s.set(r,i)}),this.toolCalls=s,console.log("updateToolCalls - final result:",this.toolCalls.size,"tool calls"),this.toolCalls.size>0&&console.log("Tool calls map keys:",Array.from(this.toolCalls.keys()))}isToolOperation(e){const t=e.tool_name||e.data&&e.data.tool_name,o=["hook","tool_use","tool","agent","response"].includes(e.type)||e.type&&e.type.includes("tool"),a="pre_tool"===e.subtype||"post_tool"===e.subtype||e.subtype&&"string"==typeof e.subtype&&e.subtype.includes("tool")||"tool_use"===e.type||"tool"===e.type;return t&&(o||a)}isFileOperation(e){let t=e.tool_name||e.data&&e.data.tool_name||"";if(!t)return!1;t=t.toLowerCase();const o=e.tool_parameters||e.data&&e.data.tool_parameters;if("bash"===t&&o){if((o.command||"").match(/\b(cat|less|more|head|tail|touch|mv|cp|rm|mkdir|ls|find)\b/))return!0}return["read","write","edit","grep","multiedit","glob","ls","bash","notebookedit"].includes(t)}extractFilePath(e){const t=e.tool_name||e.data&&e.data.tool_name;if(["Read","Write","Edit","MultiEdit","NotebookEdit"].includes(t)&&console.log("Extracting file path from event:",{tool_name:t,has_tool_parameters_top:!!e.tool_parameters,has_tool_parameters_data:!(!e.data||!e.data.tool_parameters),tool_parameters:e.tool_parameters,data_tool_parameters:e.data?.tool_parameters}),e.tool_parameters?.file_path)return e.tool_parameters.file_path;if(e.tool_parameters?.path)return e.tool_parameters.path;if(e.tool_parameters?.notebook_path)return e.tool_parameters.notebook_path;if(e.data?.tool_parameters?.file_path)return e.data.tool_parameters.file_path;if(e.data?.tool_parameters?.path)return e.data.tool_parameters.path;if(e.data?.tool_parameters?.notebook_path)return e.data.tool_parameters.notebook_path;if(e.file_path)return e.file_path;if(e.path)return e.path;if("glob"===e.tool_name?.toLowerCase()&&e.tool_parameters?.pattern)return`[glob] ${e.tool_parameters.pattern}`;if("bash"===e.tool_name?.toLowerCase()&&e.tool_parameters?.command){const t=e.tool_parameters.command,o=t.match(/(?:cat|less|more|head|tail|touch|mv|cp|rm|mkdir|ls|find|echo.*>|sed|awk|grep)(?:\s+-[a-zA-Z0-9]+)*(?:\s+[0-9]+)*\s+([^\s;|&]+)/);if(o&&o[1]){const e=o[1];if(e.startsWith("-")){const e=t.match(/(?:cat|less|more|head|tail|touch|mv|cp|rm|mkdir|ls|find|echo.*>|sed|awk|grep)(?:\s+-[^\s]+)*\s+([^-][^\s;|&]*)/);if(e&&e[1])return e[1]}return e}}return null}extractFilePathFromPair(e){let t=null;return e.pre_event&&(t=this.extractFilePath(e.pre_event)),!t&&e.post_event&&(t=this.extractFilePath(e.post_event)),t}getFileOperation(e){if(!e.tool_name)return"unknown";const t=e.tool_name.toLowerCase();switch(t){case"read":return"read";case"write":return"write";case"edit":case"multiedit":case"notebookedit":return"edit";case"grep":case"glob":return"search";case"ls":return"list";case"bash":const o=e.tool_parameters?.command||"";return o.match(/\b(cat|less|more|head|tail)\b/)?"read":o.match(/\b(touch|echo.*>|tee)\b/)?"write":o.match(/\b(sed|awk)\b/)?"edit":o.match(/\b(grep|find)\b/)?"search":o.match(/\b(ls|dir)\b/)?"list":o.match(/\b(mv|cp)\b/)?"copy/move":o.match(/\b(rm|rmdir)\b/)?"delete":o.match(/\b(mkdir)\b/)?"create":"bash";default:return t}}getFileOperationFromPair(e){return e.pre_event?this.getFileOperation(e.pre_event):e.post_event?this.getFileOperation(e.post_event):"unknown"}extractAgentFromPair(e){const t=e.pre_event||e.post_event;if(t&&this.agentInference){const e=this.agentInference.getInferredAgentForEvent(t);if(e)return{name:e.agentName||"Unknown",confidence:e.confidence||"unknown"}}return{name:t?.agent_type||t?.subagent_type||e.pre_event?.agent_type||e.post_event?.agent_type||"PM",confidence:"direct"}}getFileOperationDetailsFromPair(e){const t={};if(e.pre_event){const o=e.pre_event.tool_parameters||e.pre_event.data?.tool_parameters||{};t.parameters=o,t.tool_input=e.pre_event.tool_input}return e.post_event&&(t.result=e.post_event.result,t.success=e.post_event.success,t.error=e.post_event.error,t.exit_code=e.post_event.exit_code,t.duration_ms=e.post_event.duration_ms),t}getFileOperations(){return this.fileOperations}getToolCalls(){return this.toolCalls}getToolCallsArray(){return Array.from(this.toolCalls.entries())}getFileOperationsForFile(e){return this.fileOperations.get(e)||null}getToolCall(e){return this.toolCalls.get(e)||null}clear(){this.fileOperations.clear(),this.toolCalls.clear(),console.log("File-tool tracker cleared")}getStatistics(){return{fileOperations:this.fileOperations.size,toolCalls:this.toolCalls.size,uniqueFiles:this.fileOperations.size,totalFileOperations:Array.from(this.fileOperations.values()).reduce((e,t)=>e+t.operations.length,0)}}compareToolParameters(e,t){const o=e.tool_parameters||e.data?.tool_parameters||{},a=t.tool_parameters||t.data?.tool_parameters||{};if(0===Object.keys(o).length&&0===Object.keys(a).length)return!1;let s=0,n=0;if(["file_path","path","pattern","command","notebook_path"].forEach(e=>{const t=o[e],r=a[e];void 0===t&&void 0===r||(n++,t===r&&s++)}),n>0)return s/n>=.8;const r=Object.keys(o).sort(),i=Object.keys(a).sort();if(0===r.length&&0===i.length)return!1;if(r.length===i.length){return r.filter(e=>i.includes(e)).length>=Math.max(1,.5*r.length)}return!1}extractAgentFromEvent(e){if(this.agentInference){const t=this.agentInference.getInferredAgentForEvent(e);if(t)return{name:t.agentName||"Unknown",confidence:t.confidence||"unknown"}}return{name:e.agent_type||e.subagent_type||e.data?.agent_type||e.data?.subagent_type||"PM",confidence:"direct"}}};
2
- //# sourceMappingURL=file-tool-tracker.js.map
@@ -1,2 +0,0 @@
1
- const e=new class{constructor(){this.modal=null,this.currentFile=null,this.initialized=!1,this.contentCache=new Map}initialize(){this.initialized||(this.createModal(),this.setupEventHandlers(),this.initialized=!0,console.log("File viewer initialized"))}createModal(){if(document.body.insertAdjacentHTML("beforeend",'\n <div class="file-viewer-modal" id="file-viewer-modal">\n <div class="file-viewer-content">\n <div class="file-viewer-header">\n <h2>📄 File Viewer</h2>\n <button class="file-viewer-close" id="file-viewer-close">×</button>\n </div>\n <div class="file-viewer-path" id="file-viewer-path">\n Loading...\n </div>\n <div class="file-viewer-body">\n <pre class="file-viewer-code" id="file-viewer-code">\n <code id="file-viewer-code-content">Loading file content...</code>\n </pre>\n </div>\n <div class="file-viewer-footer">\n <div class="file-viewer-info">\n <span id="file-viewer-type">Type: --</span>\n <span id="file-viewer-lines">Lines: --</span>\n <span id="file-viewer-size">Size: --</span>\n </div>\n <button class="file-viewer-copy" id="file-viewer-copy">📋 Copy</button>\n </div>\n </div>\n </div>\n '),this.modal=document.getElementById("file-viewer-modal"),!document.getElementById("file-viewer-styles")){const e="\n <style id=\"file-viewer-styles\">\n .file-viewer-modal {\n display: none;\n position: fixed;\n top: 0;\n left: 0;\n width: 100%;\n height: 100%;\n background: rgba(0, 0, 0, 0.7);\n z-index: 10000;\n animation: fadeIn 0.2s;\n }\n\n .file-viewer-modal.show {\n display: flex;\n align-items: center;\n justify-content: center;\n }\n\n .file-viewer-content {\n background: #1e1e1e;\n border-radius: 8px;\n width: 90%;\n max-width: 1200px;\n height: 80%;\n display: flex;\n flex-direction: column;\n box-shadow: 0 4px 20px rgba(0, 0, 0, 0.5);\n }\n\n .file-viewer-header {\n display: flex;\n justify-content: space-between;\n align-items: center;\n padding: 15px 20px;\n background: #2d2d30;\n border-radius: 8px 8px 0 0;\n border-bottom: 1px solid #3e3e42;\n }\n\n .file-viewer-header h2 {\n margin: 0;\n color: #cccccc;\n font-size: 18px;\n }\n\n .file-viewer-close {\n background: none;\n border: none;\n color: #999;\n font-size: 24px;\n cursor: pointer;\n padding: 0;\n width: 30px;\n height: 30px;\n display: flex;\n align-items: center;\n justify-content: center;\n }\n\n .file-viewer-close:hover {\n color: #fff;\n }\n\n .file-viewer-path {\n padding: 10px 20px;\n background: #252526;\n color: #8b8b8b;\n font-family: 'Consolas', 'Monaco', monospace;\n font-size: 12px;\n border-bottom: 1px solid #3e3e42;\n word-break: break-all;\n }\n\n .file-viewer-body {\n flex: 1;\n overflow: auto;\n padding: 20px;\n background: #1e1e1e;\n }\n\n .file-viewer-code {\n margin: 0;\n padding: 0;\n background: transparent;\n overflow: visible;\n }\n\n .file-viewer-code code {\n font-family: 'Consolas', 'Monaco', 'Courier New', monospace;\n font-size: 13px;\n line-height: 1.5;\n color: #d4d4d4;\n white-space: pre;\n display: block;\n }\n\n .file-viewer-footer {\n padding: 15px 20px;\n background: #2d2d30;\n border-top: 1px solid #3e3e42;\n display: flex;\n justify-content: space-between;\n align-items: center;\n border-radius: 0 0 8px 8px;\n }\n\n .file-viewer-info {\n display: flex;\n gap: 20px;\n color: #8b8b8b;\n font-size: 12px;\n }\n\n .file-viewer-copy {\n background: #0e639c;\n color: white;\n border: none;\n padding: 6px 12px;\n border-radius: 4px;\n cursor: pointer;\n font-size: 12px;\n }\n\n .file-viewer-copy:hover {\n background: #1177bb;\n }\n\n .file-viewer-copy.copied {\n background: #4ec9b0;\n }\n\n .file-viewer-error {\n color: #f48771;\n padding: 20px;\n text-align: center;\n }\n\n @keyframes fadeIn {\n from { opacity: 0; }\n to { opacity: 1; }\n }\n </style>\n ";document.head.insertAdjacentHTML("beforeend",e)}}setupEventHandlers(){document.getElementById("file-viewer-close").addEventListener("click",()=>{this.hide()}),this.modal.addEventListener("click",e=>{e.target===this.modal&&this.hide()}),document.addEventListener("keydown",e=>{"Escape"===e.key&&this.modal.classList.contains("show")&&this.hide()}),document.getElementById("file-viewer-copy").addEventListener("click",()=>{this.copyContent()})}async show(e){console.log("[FileViewer] show() called with path:",e),console.log("[FileViewer] initialized:",this.initialized),this.initialized||(console.log("[FileViewer] Not initialized, initializing now..."),this.initialize()),this.currentFile=e,this.modal.classList.add("show"),document.getElementById("file-viewer-path").textContent=e,console.log("[FileViewer] Modal shown, loading file content..."),await this.loadFileContent(e)}hide(){this.modal.classList.remove("show"),this.currentFile=null}async loadFileContent(e){const n=document.getElementById("file-viewer-code-content");if(console.log("[FileViewer] loadFileContent called with path:",e),this.contentCache.has(e))return console.log("[FileViewer] Using cached content for:",e),void this.displayContent(this.contentCache.get(e));n.textContent="Loading file content...";try{if(!window.socket||!window.socket.connected)throw console.error("[FileViewer] No Socket.IO connection available"),new Error("No socket connection available. Please ensure the dashboard is connected to the monitoring server.");{console.log("[FileViewer] Using Socket.IO to load file:",e);const n=new Promise((n,i)=>{const t=setTimeout(()=>{console.error("[FileViewer] Socket.IO request timed out for:",e),i(new Error("Socket.IO request timed out"))},1e4);window.socket.once("file_content_response",e=>{clearTimeout(t),console.log("[FileViewer] Received file_content_response:",e),n(e)}),console.log("[FileViewer] Emitting read_file event with data:",{file_path:e,working_dir:window.workingDirectory||"/",max_size:5242880}),window.socket.emit("read_file",{file_path:e,working_dir:window.workingDirectory||"/",max_size:5242880})}),i=await n;if(!i.success||void 0===i.content)throw console.error("[FileViewer] Server returned error:",i.error),new Error(i.error||"Failed to load file content");console.log("[FileViewer] Successfully loaded file content, caching..."),this.contentCache.set(e,i.content),this.displayContent(i.content),this.updateFileInfo(i)}}catch(i){console.error("[FileViewer] Error loading file:",i),console.error("[FileViewer] Error stack:",i.stack),this.displayError(e,i.message)}}displayContent(e){const n=document.getElementById("file-viewer-code-content");n.textContent=e||"(Empty file)";const i=e?e.split("\n").length:0;document.getElementById("file-viewer-lines").textContent=`Lines: ${i}`;const t=e?new Blob([e]).size:0;document.getElementById("file-viewer-size").textContent=`Size: ${this.formatFileSize(t)}`;const o=this.detectFileType(this.currentFile);if(document.getElementById("file-viewer-type").textContent=`Type: ${o}`,window.Prism){const e=this.detectLanguage(this.currentFile);n.className=`language-${e}`,Prism.highlightElement(n)}}displayError(e,n){const i=`\n <div class="file-viewer-error">\n ⚠️ File content loading is not yet implemented\n \n File path: ${e}\n \n The file viewing functionality requires:\n 1. A server-side /api/file endpoint\n 2. Proper file reading permissions\n 3. Security validation for file access\n \n Error: ${n}\n \n This feature will be available once the backend API is implemented.\n </div>\n `;document.getElementById("file-viewer-code-content").innerHTML=i,document.getElementById("file-viewer-lines").textContent="Lines: --",document.getElementById("file-viewer-size").textContent="Size: --",document.getElementById("file-viewer-type").textContent="Type: --"}updateFileInfo(e){void 0!==e.lines&&(document.getElementById("file-viewer-lines").textContent=`Lines: ${e.lines}`),void 0!==e.size&&(document.getElementById("file-viewer-size").textContent=`Size: ${this.formatFileSize(e.size)}`),e.type&&(document.getElementById("file-viewer-type").textContent=`Type: ${e.type}`)}formatFileSize(e){if(0===e)return"0 Bytes";const n=Math.floor(Math.log(e)/Math.log(1024));return Math.round(e/Math.pow(1024,n)*100)/100+" "+["Bytes","KB","MB","GB"][n]}detectFileType(e){if(!e)return"Unknown";const n=e.split(".").pop()?.toLowerCase();return{py:"Python",js:"JavaScript",ts:"TypeScript",jsx:"React JSX",tsx:"React TSX",html:"HTML",css:"CSS",json:"JSON",xml:"XML",yaml:"YAML",yml:"YAML",md:"Markdown",txt:"Text",sh:"Shell Script",bash:"Bash Script",sql:"SQL",go:"Go",rs:"Rust",java:"Java",cpp:"C++",c:"C",cs:"C#",rb:"Ruby",php:"PHP"}[n]||"Text"}detectLanguage(e){if(!e)return"plaintext";const n=e.split(".").pop()?.toLowerCase();return{py:"python",js:"javascript",ts:"typescript",jsx:"jsx",tsx:"tsx",html:"html",css:"css",json:"json",xml:"xml",yaml:"yaml",yml:"yaml",md:"markdown",sh:"bash",bash:"bash",sql:"sql",go:"go",rs:"rust",java:"java",cpp:"cpp",c:"c",cs:"csharp",rb:"ruby",php:"php"}[n]||"plaintext"}async copyContent(){const e=document.getElementById("file-viewer-code-content"),n=document.getElementById("file-viewer-copy"),i=e.textContent;try{await navigator.clipboard.writeText(i);const e=n.textContent;n.textContent="✅ Copied!",n.classList.add("copied"),setTimeout(()=>{n.textContent=e,n.classList.remove("copied")},2e3)}catch(t){console.error("Failed to copy:",t),alert("Failed to copy content to clipboard")}}};window.showFileViewerModal||(window.showFileViewerModal=n=>{console.log("[FileViewer] showFileViewerModal called with path:",n),e.show(n)}),window.fileViewerInstance=e,"undefined"!=typeof window&&(window.FileViewer=e,"loading"===document.readyState?document.addEventListener("DOMContentLoaded",()=>{e.initialize()}):e.initialize());
2
- //# sourceMappingURL=file-viewer.js.map
@@ -1,2 +0,0 @@
1
- window.HUDLibraryLoader=new class{constructor(){this.loadedLibraries=new Set,this.loadingPromises=new Map,this.loadingCallbacks=new Map,this.libraries=[{name:"cytoscape",url:"https://unpkg.com/cytoscape@3.26.0/dist/cytoscape.min.js",globalCheck:()=>void 0!==window.cytoscape,dependencies:[]},{name:"dagre",url:"https://unpkg.com/dagre@0.8.5/dist/dagre.min.js",globalCheck:()=>void 0!==window.dagre,dependencies:[]},{name:"cytoscape-dagre",url:"https://unpkg.com/cytoscape-dagre@2.5.0/cytoscape-dagre.js",globalCheck:()=>void 0!==window.cytoscapeDagre,dependencies:["cytoscape","dagre"]}]}loadLibrary(e){if(e.globalCheck())return this.loadedLibraries.add(e.name),Promise.resolve();if(this.loadingPromises.has(e.name))return this.loadingPromises.get(e.name);console.log(`Loading library: ${e.name} from ${e.url}`);const r=new Promise((r,a)=>{const i=document.createElement("script");i.src=e.url,i.async=!0,i.onload=()=>{if(e.globalCheck())console.log(`Successfully loaded library: ${e.name}`),this.loadedLibraries.add(e.name),this.loadingPromises.delete(e.name),r();else{const r=new Error(`Library ${e.name} failed global check after loading`);console.error(r),this.loadingPromises.delete(e.name),a(r)}},i.onerror=()=>{const r=new Error(`Failed to load library: ${e.name} from ${e.url}`);console.error(r),this.loadingPromises.delete(e.name),a(r)},document.head.appendChild(i)});return this.loadingPromises.set(e.name,r),r}async loadDependencies(e){const r=e.map(e=>{const r=this.libraries.find(r=>r.name===e);if(!r)throw new Error(`Dependency ${e} not found in library configuration`);return this.loadLibraryWithDependencies(r)});return Promise.all(r)}async loadLibraryWithDependencies(e){return e.dependencies.length>0&&await this.loadDependencies(e.dependencies),this.loadLibrary(e)}async loadHUDLibraries(e=null){console.log("Starting HUD libraries loading...");try{for(let a=0;a<this.libraries.length;a++){const r=this.libraries[a];e&&e({library:r.name,current:a+1,total:this.libraries.length,message:`Loading ${r.name}...`}),await this.loadLibraryWithDependencies(r)}const r=this.libraries.filter(e=>!e.globalCheck());if(r.length>0)throw new Error(`Failed to load libraries: ${r.map(e=>e.name).join(", ")}`);return console.log("All HUD libraries loaded successfully"),e&&e({library:"complete",current:this.libraries.length,total:this.libraries.length,message:"All libraries loaded successfully"}),!0}catch(r){throw console.error("Failed to load HUD libraries:",r),e&&e({library:"error",current:0,total:this.libraries.length,message:`Error: ${r.message}`,error:r}),r}}areLibrariesLoaded(){return this.libraries.every(e=>e.globalCheck())}getLoadingStatus(){return{loaded:Array.from(this.loadedLibraries),loading:Array.from(this.loadingPromises.keys()),total:this.libraries.length,allLoaded:this.areLibrariesLoaded()}}reset(){this.loadedLibraries.clear(),this.loadingPromises.clear(),this.loadingCallbacks.clear()}};
2
- //# sourceMappingURL=hud-library-loader.js.map