claude-code-workflow 6.2.2 → 6.2.3
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.
- package/ccw/dist/cli.d.ts +2 -0
- package/ccw/dist/cli.d.ts.map +1 -0
- package/ccw/dist/cli.js +219 -0
- package/ccw/dist/cli.js.map +1 -0
- package/ccw/dist/commands/cli.d.ts +32 -0
- package/ccw/dist/commands/cli.d.ts.map +1 -0
- package/ccw/dist/commands/cli.js +619 -0
- package/ccw/dist/commands/cli.js.map +1 -0
- package/ccw/dist/commands/core-memory.d.ts +32 -0
- package/ccw/dist/commands/core-memory.d.ts.map +1 -0
- package/ccw/dist/commands/core-memory.js +640 -0
- package/ccw/dist/commands/core-memory.js.map +1 -0
- package/ccw/dist/commands/hook.d.ts +16 -0
- package/ccw/dist/commands/hook.d.ts.map +1 -0
- package/ccw/dist/commands/hook.js +276 -0
- package/ccw/dist/commands/hook.js.map +1 -0
- package/ccw/dist/commands/install.d.ts +12 -0
- package/ccw/dist/commands/install.d.ts.map +1 -0
- package/ccw/dist/commands/install.js +443 -0
- package/ccw/dist/commands/install.js.map +1 -0
- package/ccw/dist/commands/list.d.ts +5 -0
- package/ccw/dist/commands/list.d.ts.map +1 -0
- package/ccw/dist/commands/list.js +32 -0
- package/ccw/dist/commands/list.js.map +1 -0
- package/ccw/dist/commands/memory.d.ts +57 -0
- package/ccw/dist/commands/memory.d.ts.map +1 -0
- package/ccw/dist/commands/memory.js +890 -0
- package/ccw/dist/commands/memory.js.map +1 -0
- package/ccw/dist/commands/serve.d.ts +12 -0
- package/ccw/dist/commands/serve.d.ts.map +1 -0
- package/ccw/dist/commands/serve.js +63 -0
- package/ccw/dist/commands/serve.js.map +1 -0
- package/ccw/dist/commands/session-path-resolver.d.ts +45 -0
- package/ccw/dist/commands/session-path-resolver.d.ts.map +1 -0
- package/ccw/dist/commands/session-path-resolver.js +302 -0
- package/ccw/dist/commands/session-path-resolver.js.map +1 -0
- package/ccw/dist/commands/session.d.ts +12 -0
- package/ccw/dist/commands/session.d.ts.map +1 -0
- package/ccw/dist/commands/session.js +954 -0
- package/ccw/dist/commands/session.js.map +1 -0
- package/ccw/dist/commands/stop.d.ts +11 -0
- package/ccw/dist/commands/stop.d.ts.map +1 -0
- package/ccw/dist/commands/stop.js +96 -0
- package/ccw/dist/commands/stop.js.map +1 -0
- package/ccw/dist/commands/tool.d.ts +29 -0
- package/ccw/dist/commands/tool.d.ts.map +1 -0
- package/ccw/dist/commands/tool.js +173 -0
- package/ccw/dist/commands/tool.js.map +1 -0
- package/ccw/dist/commands/uninstall.d.ts +9 -0
- package/ccw/dist/commands/uninstall.d.ts.map +1 -0
- package/ccw/dist/commands/uninstall.js +239 -0
- package/ccw/dist/commands/uninstall.js.map +1 -0
- package/ccw/dist/commands/upgrade.d.ts +10 -0
- package/ccw/dist/commands/upgrade.d.ts.map +1 -0
- package/ccw/dist/commands/upgrade.js +288 -0
- package/ccw/dist/commands/upgrade.js.map +1 -0
- package/ccw/dist/commands/view.d.ts +14 -0
- package/ccw/dist/commands/view.d.ts.map +1 -0
- package/ccw/dist/commands/view.js +100 -0
- package/ccw/dist/commands/view.js.map +1 -0
- package/ccw/dist/config/storage-paths.d.ts +184 -0
- package/ccw/dist/config/storage-paths.d.ts.map +1 -0
- package/ccw/dist/config/storage-paths.js +536 -0
- package/ccw/dist/config/storage-paths.js.map +1 -0
- package/ccw/dist/core/cache-manager.d.ts +80 -0
- package/ccw/dist/core/cache-manager.d.ts.map +1 -0
- package/ccw/dist/core/cache-manager.js +260 -0
- package/ccw/dist/core/cache-manager.js.map +1 -0
- package/ccw/dist/core/claude-freshness.d.ts +53 -0
- package/ccw/dist/core/claude-freshness.d.ts.map +1 -0
- package/ccw/dist/core/claude-freshness.js +232 -0
- package/ccw/dist/core/claude-freshness.js.map +1 -0
- package/ccw/dist/core/core-memory-store.d.ts +320 -0
- package/ccw/dist/core/core-memory-store.d.ts.map +1 -0
- package/ccw/dist/core/core-memory-store.js +1177 -0
- package/ccw/dist/core/core-memory-store.js.map +1 -0
- package/ccw/dist/core/dashboard-generator-patch.d.ts +2 -0
- package/ccw/dist/core/dashboard-generator-patch.d.ts.map +1 -0
- package/ccw/dist/core/dashboard-generator-patch.js +48 -0
- package/ccw/dist/core/dashboard-generator-patch.js.map +1 -0
- package/ccw/dist/core/dashboard-generator.d.ts +8 -0
- package/ccw/dist/core/dashboard-generator.d.ts.map +1 -0
- package/ccw/dist/core/dashboard-generator.js +695 -0
- package/ccw/dist/core/dashboard-generator.js.map +1 -0
- package/ccw/dist/core/data-aggregator.d.ts +145 -0
- package/ccw/dist/core/data-aggregator.d.ts.map +1 -0
- package/ccw/dist/core/data-aggregator.js +416 -0
- package/ccw/dist/core/data-aggregator.js.map +1 -0
- package/ccw/dist/core/history-importer.d.ts +102 -0
- package/ccw/dist/core/history-importer.d.ts.map +1 -0
- package/ccw/dist/core/history-importer.js +493 -0
- package/ccw/dist/core/history-importer.js.map +1 -0
- package/ccw/dist/core/lite-scanner-complete.d.ts +81 -0
- package/ccw/dist/core/lite-scanner-complete.d.ts.map +1 -0
- package/ccw/dist/core/lite-scanner-complete.js +368 -0
- package/ccw/dist/core/lite-scanner-complete.js.map +1 -0
- package/ccw/dist/core/lite-scanner.d.ts +81 -0
- package/ccw/dist/core/lite-scanner.d.ts.map +1 -0
- package/ccw/dist/core/lite-scanner.js +368 -0
- package/ccw/dist/core/lite-scanner.js.map +1 -0
- package/ccw/dist/core/manifest.d.ts +88 -0
- package/ccw/dist/core/manifest.d.ts.map +1 -0
- package/ccw/dist/core/manifest.js +214 -0
- package/ccw/dist/core/manifest.js.map +1 -0
- package/ccw/dist/core/memory-embedder-bridge.d.ts +83 -0
- package/ccw/dist/core/memory-embedder-bridge.d.ts.map +1 -0
- package/ccw/dist/core/memory-embedder-bridge.js +181 -0
- package/ccw/dist/core/memory-embedder-bridge.js.map +1 -0
- package/ccw/dist/core/memory-store.d.ts +249 -0
- package/ccw/dist/core/memory-store.d.ts.map +1 -0
- package/ccw/dist/core/memory-store.js +781 -0
- package/ccw/dist/core/memory-store.js.map +1 -0
- package/ccw/dist/core/routes/ccw-routes.d.ts +20 -0
- package/ccw/dist/core/routes/ccw-routes.d.ts.map +1 -0
- package/ccw/dist/core/routes/ccw-routes.js +70 -0
- package/ccw/dist/core/routes/ccw-routes.js.map +1 -0
- package/ccw/dist/core/routes/claude-routes.d.ts +19 -0
- package/ccw/dist/core/routes/claude-routes.d.ts.map +1 -0
- package/ccw/dist/core/routes/claude-routes.js +1017 -0
- package/ccw/dist/core/routes/claude-routes.js.map +1 -0
- package/ccw/dist/core/routes/cli-routes.d.ts +20 -0
- package/ccw/dist/core/routes/cli-routes.d.ts.map +1 -0
- package/ccw/dist/core/routes/cli-routes.js +468 -0
- package/ccw/dist/core/routes/cli-routes.js.map +1 -0
- package/ccw/dist/core/routes/codexlens-routes.d.ts +20 -0
- package/ccw/dist/core/routes/codexlens-routes.d.ts.map +1 -0
- package/ccw/dist/core/routes/codexlens-routes.js +754 -0
- package/ccw/dist/core/routes/codexlens-routes.js.map +1 -0
- package/ccw/dist/core/routes/core-memory-routes.d.ts +21 -0
- package/ccw/dist/core/routes/core-memory-routes.d.ts.map +1 -0
- package/ccw/dist/core/routes/core-memory-routes.js +520 -0
- package/ccw/dist/core/routes/core-memory-routes.js.map +1 -0
- package/ccw/dist/core/routes/files-routes.d.ts +20 -0
- package/ccw/dist/core/routes/files-routes.d.ts.map +1 -0
- package/ccw/dist/core/routes/files-routes.js +374 -0
- package/ccw/dist/core/routes/files-routes.js.map +1 -0
- package/ccw/dist/core/routes/graph-routes.d.ts +20 -0
- package/ccw/dist/core/routes/graph-routes.d.ts.map +1 -0
- package/ccw/dist/core/routes/graph-routes.js +517 -0
- package/ccw/dist/core/routes/graph-routes.js.map +1 -0
- package/ccw/dist/core/routes/help-routes.d.ts +20 -0
- package/ccw/dist/core/routes/help-routes.d.ts.map +1 -0
- package/ccw/dist/core/routes/help-routes.js +250 -0
- package/ccw/dist/core/routes/help-routes.js.map +1 -0
- package/ccw/dist/core/routes/hooks-routes.d.ts +21 -0
- package/ccw/dist/core/routes/hooks-routes.d.ts.map +1 -0
- package/ccw/dist/core/routes/hooks-routes.js +346 -0
- package/ccw/dist/core/routes/hooks-routes.js.map +1 -0
- package/ccw/dist/core/routes/mcp-routes.d.ts +20 -0
- package/ccw/dist/core/routes/mcp-routes.d.ts.map +1 -0
- package/ccw/dist/core/routes/mcp-routes.js +1129 -0
- package/ccw/dist/core/routes/mcp-routes.js.map +1 -0
- package/ccw/dist/core/routes/mcp-templates-db.d.ts +54 -0
- package/ccw/dist/core/routes/mcp-templates-db.d.ts.map +1 -0
- package/ccw/dist/core/routes/mcp-templates-db.js +226 -0
- package/ccw/dist/core/routes/mcp-templates-db.js.map +1 -0
- package/ccw/dist/core/routes/memory-routes.d.ts +21 -0
- package/ccw/dist/core/routes/memory-routes.d.ts.map +1 -0
- package/ccw/dist/core/routes/memory-routes.js +1095 -0
- package/ccw/dist/core/routes/memory-routes.js.map +1 -0
- package/ccw/dist/core/routes/rules-routes.d.ts +20 -0
- package/ccw/dist/core/routes/rules-routes.d.ts.map +1 -0
- package/ccw/dist/core/routes/rules-routes.js +442 -0
- package/ccw/dist/core/routes/rules-routes.js.map +1 -0
- package/ccw/dist/core/routes/session-routes.d.ts +20 -0
- package/ccw/dist/core/routes/session-routes.d.ts.map +1 -0
- package/ccw/dist/core/routes/session-routes.js +423 -0
- package/ccw/dist/core/routes/session-routes.js.map +1 -0
- package/ccw/dist/core/routes/skills-routes.d.ts +20 -0
- package/ccw/dist/core/routes/skills-routes.d.ts.map +1 -0
- package/ccw/dist/core/routes/skills-routes.js +533 -0
- package/ccw/dist/core/routes/skills-routes.js.map +1 -0
- package/ccw/dist/core/routes/status-routes.d.ts +20 -0
- package/ccw/dist/core/routes/status-routes.d.ts.map +1 -0
- package/ccw/dist/core/routes/status-routes.js +38 -0
- package/ccw/dist/core/routes/status-routes.js.map +1 -0
- package/ccw/dist/core/routes/system-routes.d.ts +22 -0
- package/ccw/dist/core/routes/system-routes.d.ts.map +1 -0
- package/ccw/dist/core/routes/system-routes.js +354 -0
- package/ccw/dist/core/routes/system-routes.js.map +1 -0
- package/ccw/dist/core/server.d.ts +17 -0
- package/ccw/dist/core/server.d.ts.map +1 -0
- package/ccw/dist/core/server.js +386 -0
- package/ccw/dist/core/server.js.map +1 -0
- package/ccw/dist/core/session-clustering-service.d.ts +153 -0
- package/ccw/dist/core/session-clustering-service.d.ts.map +1 -0
- package/ccw/dist/core/session-clustering-service.js +1065 -0
- package/ccw/dist/core/session-clustering-service.js.map +1 -0
- package/ccw/dist/core/session-scanner.d.ts +32 -0
- package/ccw/dist/core/session-scanner.d.ts.map +1 -0
- package/ccw/dist/core/session-scanner.js +253 -0
- package/ccw/dist/core/session-scanner.js.map +1 -0
- package/ccw/dist/core/websocket.d.ts +23 -0
- package/ccw/dist/core/websocket.d.ts.map +1 -0
- package/ccw/dist/core/websocket.js +168 -0
- package/ccw/dist/core/websocket.js.map +1 -0
- package/ccw/dist/index.d.ts +10 -0
- package/ccw/dist/index.d.ts.map +1 -0
- package/ccw/dist/index.js +10 -0
- package/ccw/dist/index.js.map +1 -0
- package/ccw/dist/mcp-server/index.d.ts +7 -0
- package/ccw/dist/mcp-server/index.d.ts.map +1 -0
- package/ccw/dist/mcp-server/index.js +157 -0
- package/ccw/dist/mcp-server/index.js.map +1 -0
- package/ccw/dist/tools/classify-folders.d.ts +26 -0
- package/ccw/dist/tools/classify-folders.d.ts.map +1 -0
- package/ccw/dist/tools/classify-folders.js +201 -0
- package/ccw/dist/tools/classify-folders.js.map +1 -0
- package/ccw/dist/tools/cli-config-manager.d.ts +62 -0
- package/ccw/dist/tools/cli-config-manager.d.ts.map +1 -0
- package/ccw/dist/tools/cli-config-manager.js +221 -0
- package/ccw/dist/tools/cli-config-manager.js.map +1 -0
- package/ccw/dist/tools/cli-executor.d.ts +373 -0
- package/ccw/dist/tools/cli-executor.d.ts.map +1 -0
- package/ccw/dist/tools/cli-executor.js +1625 -0
- package/ccw/dist/tools/cli-executor.js.map +1 -0
- package/ccw/dist/tools/cli-history-store.d.ts +330 -0
- package/ccw/dist/tools/cli-history-store.d.ts.map +1 -0
- package/ccw/dist/tools/cli-history-store.js +916 -0
- package/ccw/dist/tools/cli-history-store.js.map +1 -0
- package/ccw/dist/tools/codex-lens.d.ts +118 -0
- package/ccw/dist/tools/codex-lens.d.ts.map +1 -0
- package/ccw/dist/tools/codex-lens.js +962 -0
- package/ccw/dist/tools/codex-lens.js.map +1 -0
- package/ccw/dist/tools/convert-tokens-to-css.d.ts +14 -0
- package/ccw/dist/tools/convert-tokens-to-css.d.ts.map +1 -0
- package/ccw/dist/tools/convert-tokens-to-css.js +244 -0
- package/ccw/dist/tools/convert-tokens-to-css.js.map +1 -0
- package/ccw/dist/tools/core-memory.d.ts +66 -0
- package/ccw/dist/tools/core-memory.d.ts.map +1 -0
- package/ccw/dist/tools/core-memory.js +324 -0
- package/ccw/dist/tools/core-memory.js.map +1 -0
- package/ccw/dist/tools/detect-changed-modules.d.ts +24 -0
- package/ccw/dist/tools/detect-changed-modules.d.ts.map +1 -0
- package/ccw/dist/tools/detect-changed-modules.js +277 -0
- package/ccw/dist/tools/detect-changed-modules.js.map +1 -0
- package/ccw/dist/tools/discover-design-files.d.ts +36 -0
- package/ccw/dist/tools/discover-design-files.d.ts.map +1 -0
- package/ccw/dist/tools/discover-design-files.js +147 -0
- package/ccw/dist/tools/discover-design-files.js.map +1 -0
- package/ccw/dist/tools/edit-file.d.ts +28 -0
- package/ccw/dist/tools/edit-file.d.ts.map +1 -0
- package/ccw/dist/tools/edit-file.js +479 -0
- package/ccw/dist/tools/edit-file.js.map +1 -0
- package/ccw/dist/tools/generate-module-docs.d.ts +22 -0
- package/ccw/dist/tools/generate-module-docs.d.ts.map +1 -0
- package/ccw/dist/tools/generate-module-docs.js +379 -0
- package/ccw/dist/tools/generate-module-docs.js.map +1 -0
- package/ccw/dist/tools/get-modules-by-depth.d.ts +15 -0
- package/ccw/dist/tools/get-modules-by-depth.d.ts.map +1 -0
- package/ccw/dist/tools/get-modules-by-depth.js +296 -0
- package/ccw/dist/tools/get-modules-by-depth.js.map +1 -0
- package/ccw/dist/tools/index.d.ts +55 -0
- package/ccw/dist/tools/index.d.ts.map +1 -0
- package/ccw/dist/tools/index.js +304 -0
- package/ccw/dist/tools/index.js.map +1 -0
- package/ccw/dist/tools/native-session-discovery.d.ts +97 -0
- package/ccw/dist/tools/native-session-discovery.d.ts.map +1 -0
- package/ccw/dist/tools/native-session-discovery.js +700 -0
- package/ccw/dist/tools/native-session-discovery.js.map +1 -0
- package/ccw/dist/tools/notifier.d.ts +50 -0
- package/ccw/dist/tools/notifier.d.ts.map +1 -0
- package/ccw/dist/tools/notifier.js +90 -0
- package/ccw/dist/tools/notifier.js.map +1 -0
- package/ccw/dist/tools/read-file.d.ts +32 -0
- package/ccw/dist/tools/read-file.d.ts.map +1 -0
- package/ccw/dist/tools/read-file.js +329 -0
- package/ccw/dist/tools/read-file.js.map +1 -0
- package/ccw/dist/tools/resume-strategy.d.ts +48 -0
- package/ccw/dist/tools/resume-strategy.d.ts.map +1 -0
- package/ccw/dist/tools/resume-strategy.js +248 -0
- package/ccw/dist/tools/resume-strategy.js.map +1 -0
- package/ccw/dist/tools/session-content-parser.d.ts +58 -0
- package/ccw/dist/tools/session-content-parser.d.ts.map +1 -0
- package/ccw/dist/tools/session-content-parser.js +420 -0
- package/ccw/dist/tools/session-content-parser.js.map +1 -0
- package/ccw/dist/tools/session-manager.d.ts +9 -0
- package/ccw/dist/tools/session-manager.d.ts.map +1 -0
- package/ccw/dist/tools/session-manager.js +834 -0
- package/ccw/dist/tools/session-manager.js.map +1 -0
- package/ccw/dist/tools/smart-context.d.ts +35 -0
- package/ccw/dist/tools/smart-context.d.ts.map +1 -0
- package/ccw/dist/tools/smart-context.js +182 -0
- package/ccw/dist/tools/smart-context.js.map +1 -0
- package/ccw/dist/tools/smart-search.d.ts +105 -0
- package/ccw/dist/tools/smart-search.d.ts.map +1 -0
- package/ccw/dist/tools/smart-search.js +1753 -0
- package/ccw/dist/tools/smart-search.js.map +1 -0
- package/ccw/dist/tools/storage-manager.d.ts +114 -0
- package/ccw/dist/tools/storage-manager.d.ts.map +1 -0
- package/ccw/dist/tools/storage-manager.js +392 -0
- package/ccw/dist/tools/storage-manager.js.map +1 -0
- package/ccw/dist/tools/ui-generate-preview.d.ts +39 -0
- package/ccw/dist/tools/ui-generate-preview.d.ts.map +1 -0
- package/ccw/dist/tools/ui-generate-preview.js +300 -0
- package/ccw/dist/tools/ui-generate-preview.js.map +1 -0
- package/ccw/dist/tools/ui-instantiate-prototypes.d.ts +75 -0
- package/ccw/dist/tools/ui-instantiate-prototypes.d.ts.map +1 -0
- package/ccw/dist/tools/ui-instantiate-prototypes.js +256 -0
- package/ccw/dist/tools/ui-instantiate-prototypes.js.map +1 -0
- package/ccw/dist/tools/update-module-claude.d.ts +80 -0
- package/ccw/dist/tools/update-module-claude.d.ts.map +1 -0
- package/ccw/dist/tools/update-module-claude.js +351 -0
- package/ccw/dist/tools/update-module-claude.js.map +1 -0
- package/ccw/dist/tools/write-file.d.ts +19 -0
- package/ccw/dist/tools/write-file.d.ts.map +1 -0
- package/ccw/dist/tools/write-file.js +193 -0
- package/ccw/dist/tools/write-file.js.map +1 -0
- package/ccw/dist/types/config.d.ts +11 -0
- package/ccw/dist/types/config.d.ts.map +1 -0
- package/ccw/dist/types/config.js +2 -0
- package/ccw/dist/types/config.js.map +1 -0
- package/ccw/dist/types/index.d.ts +4 -0
- package/ccw/dist/types/index.d.ts.map +1 -0
- package/ccw/dist/types/index.js +4 -0
- package/ccw/dist/types/index.js.map +1 -0
- package/ccw/dist/types/session.d.ts +20 -0
- package/ccw/dist/types/session.d.ts.map +1 -0
- package/ccw/dist/types/session.js +2 -0
- package/ccw/dist/types/session.js.map +1 -0
- package/ccw/dist/types/tool.d.ts +36 -0
- package/ccw/dist/types/tool.d.ts.map +1 -0
- package/ccw/dist/types/tool.js +11 -0
- package/ccw/dist/types/tool.js.map +1 -0
- package/ccw/dist/utils/browser-launcher.d.ts +13 -0
- package/ccw/dist/utils/browser-launcher.d.ts.map +1 -0
- package/ccw/dist/utils/browser-launcher.js +60 -0
- package/ccw/dist/utils/browser-launcher.js.map +1 -0
- package/ccw/dist/utils/file-utils.d.ts +25 -0
- package/ccw/dist/utils/file-utils.d.ts.map +1 -0
- package/ccw/dist/utils/file-utils.js +48 -0
- package/ccw/dist/utils/file-utils.js.map +1 -0
- package/ccw/dist/utils/path-resolver.d.ts +80 -0
- package/ccw/dist/utils/path-resolver.d.ts.map +1 -0
- package/ccw/dist/utils/path-resolver.js +260 -0
- package/ccw/dist/utils/path-resolver.js.map +1 -0
- package/ccw/dist/utils/path-validator.d.ts +49 -0
- package/ccw/dist/utils/path-validator.d.ts.map +1 -0
- package/ccw/dist/utils/path-validator.js +123 -0
- package/ccw/dist/utils/path-validator.js.map +1 -0
- package/ccw/dist/utils/ui.d.ts +62 -0
- package/ccw/dist/utils/ui.d.ts.map +1 -0
- package/ccw/dist/utils/ui.js +129 -0
- package/ccw/dist/utils/ui.js.map +1 -0
- package/ccw/package.json +1 -1
- package/package.json +1 -1
|
@@ -0,0 +1,754 @@
|
|
|
1
|
+
import { checkVenvStatus, bootstrapVenv, executeCodexLens, checkSemanticStatus, installSemantic, uninstallCodexLens, cancelIndexing, isIndexingInProgress } from '../../tools/codex-lens.js';
|
|
2
|
+
/**
|
|
3
|
+
* Strip ANSI color codes from string
|
|
4
|
+
* Rich library adds color codes even with --json flag
|
|
5
|
+
*/
|
|
6
|
+
function stripAnsiCodes(str) {
|
|
7
|
+
// ANSI escape code pattern: \x1b[...m or \x1b]...
|
|
8
|
+
return str.replace(/\x1b\[[0-9;]*m/g, '')
|
|
9
|
+
.replace(/\x1b\][0-9;]*\x07/g, '')
|
|
10
|
+
.replace(/\x1b\][^\x07]*\x07/g, '');
|
|
11
|
+
}
|
|
12
|
+
/**
|
|
13
|
+
* Format file size to human readable string
|
|
14
|
+
*/
|
|
15
|
+
function formatSize(bytes) {
|
|
16
|
+
if (bytes === 0)
|
|
17
|
+
return '0 B';
|
|
18
|
+
const units = ['B', 'KB', 'MB', 'GB', 'TB'];
|
|
19
|
+
const k = 1024;
|
|
20
|
+
const i = Math.floor(Math.log(bytes) / Math.log(k));
|
|
21
|
+
const size = parseFloat((bytes / Math.pow(k, i)).toFixed(i < 2 ? 0 : 1));
|
|
22
|
+
return size + ' ' + units[i];
|
|
23
|
+
}
|
|
24
|
+
/**
|
|
25
|
+
* Extract JSON from CLI output that may contain logging messages
|
|
26
|
+
* CodexLens CLI outputs logs like "INFO ..." before the JSON
|
|
27
|
+
* Also strips ANSI color codes that Rich library adds
|
|
28
|
+
*/
|
|
29
|
+
function extractJSON(output) {
|
|
30
|
+
// Strip ANSI color codes first
|
|
31
|
+
const cleanOutput = stripAnsiCodes(output);
|
|
32
|
+
// Find the first { or [ character (start of JSON)
|
|
33
|
+
const jsonStart = cleanOutput.search(/[{\[]/);
|
|
34
|
+
if (jsonStart === -1) {
|
|
35
|
+
throw new Error('No JSON found in output');
|
|
36
|
+
}
|
|
37
|
+
// Extract everything from the first { or [ onwards
|
|
38
|
+
const jsonString = cleanOutput.substring(jsonStart);
|
|
39
|
+
return JSON.parse(jsonString);
|
|
40
|
+
}
|
|
41
|
+
/**
|
|
42
|
+
* Handle CodexLens routes
|
|
43
|
+
* @returns true if route was handled, false otherwise
|
|
44
|
+
*/
|
|
45
|
+
export async function handleCodexLensRoutes(ctx) {
|
|
46
|
+
const { pathname, url, req, res, initialPath, handlePostRequest, broadcastToClients } = ctx;
|
|
47
|
+
// API: CodexLens Index List - Get all indexed projects with details
|
|
48
|
+
if (pathname === '/api/codexlens/indexes') {
|
|
49
|
+
try {
|
|
50
|
+
// Get config for index directory path
|
|
51
|
+
const configResult = await executeCodexLens(['config', '--json']);
|
|
52
|
+
let indexDir = '';
|
|
53
|
+
if (configResult.success) {
|
|
54
|
+
try {
|
|
55
|
+
const config = extractJSON(configResult.output);
|
|
56
|
+
if (config.success && config.result) {
|
|
57
|
+
// CLI returns index_dir (not index_root)
|
|
58
|
+
indexDir = config.result.index_dir || config.result.index_root || '';
|
|
59
|
+
}
|
|
60
|
+
}
|
|
61
|
+
catch (e) {
|
|
62
|
+
console.error('[CodexLens] Failed to parse config for index list:', e.message);
|
|
63
|
+
}
|
|
64
|
+
}
|
|
65
|
+
// Get project list using 'projects list' command
|
|
66
|
+
const projectsResult = await executeCodexLens(['projects', 'list', '--json']);
|
|
67
|
+
let indexes = [];
|
|
68
|
+
let totalSize = 0;
|
|
69
|
+
let vectorIndexCount = 0;
|
|
70
|
+
let normalIndexCount = 0;
|
|
71
|
+
if (projectsResult.success) {
|
|
72
|
+
try {
|
|
73
|
+
const projectsData = extractJSON(projectsResult.output);
|
|
74
|
+
if (projectsData.success && Array.isArray(projectsData.result)) {
|
|
75
|
+
const { statSync, existsSync } = await import('fs');
|
|
76
|
+
const { basename, join } = await import('path');
|
|
77
|
+
for (const project of projectsData.result) {
|
|
78
|
+
// Skip test/temp projects
|
|
79
|
+
if (project.source_root && (project.source_root.includes('\\Temp\\') ||
|
|
80
|
+
project.source_root.includes('/tmp/') ||
|
|
81
|
+
project.total_files === 0)) {
|
|
82
|
+
continue;
|
|
83
|
+
}
|
|
84
|
+
let projectSize = 0;
|
|
85
|
+
let hasVectorIndex = false;
|
|
86
|
+
let hasNormalIndex = true; // All projects have FTS index
|
|
87
|
+
let lastModified = null;
|
|
88
|
+
// Try to get actual index size from index_root
|
|
89
|
+
if (project.index_root && existsSync(project.index_root)) {
|
|
90
|
+
try {
|
|
91
|
+
const { readdirSync } = await import('fs');
|
|
92
|
+
const files = readdirSync(project.index_root);
|
|
93
|
+
for (const file of files) {
|
|
94
|
+
try {
|
|
95
|
+
const filePath = join(project.index_root, file);
|
|
96
|
+
const stat = statSync(filePath);
|
|
97
|
+
projectSize += stat.size;
|
|
98
|
+
if (!lastModified || stat.mtime > lastModified) {
|
|
99
|
+
lastModified = stat.mtime;
|
|
100
|
+
}
|
|
101
|
+
// Check for vector/embedding files
|
|
102
|
+
if (file.includes('vector') || file.includes('embedding') ||
|
|
103
|
+
file.endsWith('.faiss') || file.endsWith('.npy') ||
|
|
104
|
+
file.includes('semantic_chunks')) {
|
|
105
|
+
hasVectorIndex = true;
|
|
106
|
+
}
|
|
107
|
+
}
|
|
108
|
+
catch (e) {
|
|
109
|
+
// Skip files we can't stat
|
|
110
|
+
}
|
|
111
|
+
}
|
|
112
|
+
}
|
|
113
|
+
catch (e) {
|
|
114
|
+
// Can't read index directory
|
|
115
|
+
}
|
|
116
|
+
}
|
|
117
|
+
if (hasVectorIndex)
|
|
118
|
+
vectorIndexCount++;
|
|
119
|
+
if (hasNormalIndex)
|
|
120
|
+
normalIndexCount++;
|
|
121
|
+
totalSize += projectSize;
|
|
122
|
+
// Use source_root as the display name
|
|
123
|
+
const displayName = project.source_root ? basename(project.source_root) : `project_${project.id}`;
|
|
124
|
+
indexes.push({
|
|
125
|
+
id: displayName,
|
|
126
|
+
path: project.source_root || '',
|
|
127
|
+
indexPath: project.index_root || '',
|
|
128
|
+
size: projectSize,
|
|
129
|
+
sizeFormatted: formatSize(projectSize),
|
|
130
|
+
fileCount: project.total_files || 0,
|
|
131
|
+
dirCount: project.total_dirs || 0,
|
|
132
|
+
hasVectorIndex,
|
|
133
|
+
hasNormalIndex,
|
|
134
|
+
status: project.status || 'active',
|
|
135
|
+
lastModified: lastModified ? lastModified.toISOString() : null
|
|
136
|
+
});
|
|
137
|
+
}
|
|
138
|
+
// Sort by file count (most files first), then by name
|
|
139
|
+
indexes.sort((a, b) => {
|
|
140
|
+
if (b.fileCount !== a.fileCount)
|
|
141
|
+
return b.fileCount - a.fileCount;
|
|
142
|
+
return a.id.localeCompare(b.id);
|
|
143
|
+
});
|
|
144
|
+
}
|
|
145
|
+
}
|
|
146
|
+
catch (e) {
|
|
147
|
+
console.error('[CodexLens] Failed to parse projects list:', e.message);
|
|
148
|
+
}
|
|
149
|
+
}
|
|
150
|
+
// Also get summary stats from status command
|
|
151
|
+
const statusResult = await executeCodexLens(['status', '--json']);
|
|
152
|
+
let statusSummary = {};
|
|
153
|
+
if (statusResult.success) {
|
|
154
|
+
try {
|
|
155
|
+
const status = extractJSON(statusResult.output);
|
|
156
|
+
if (status.success && status.result) {
|
|
157
|
+
statusSummary = {
|
|
158
|
+
totalProjects: status.result.projects_count || indexes.length,
|
|
159
|
+
totalFiles: status.result.total_files || 0,
|
|
160
|
+
totalDirs: status.result.total_dirs || 0,
|
|
161
|
+
// Keep calculated totalSize for consistency with per-project sizes
|
|
162
|
+
// status.index_size_bytes includes shared resources (models, cache)
|
|
163
|
+
indexSizeBytes: totalSize,
|
|
164
|
+
indexSizeMb: totalSize / (1024 * 1024),
|
|
165
|
+
embeddings: status.result.embeddings || {},
|
|
166
|
+
// Store full index dir size separately for reference
|
|
167
|
+
fullIndexDirSize: status.result.index_size_bytes || 0,
|
|
168
|
+
fullIndexDirSizeFormatted: formatSize(status.result.index_size_bytes || 0)
|
|
169
|
+
};
|
|
170
|
+
}
|
|
171
|
+
}
|
|
172
|
+
catch (e) {
|
|
173
|
+
console.error('[CodexLens] Failed to parse status:', e.message);
|
|
174
|
+
}
|
|
175
|
+
}
|
|
176
|
+
res.writeHead(200, { 'Content-Type': 'application/json' });
|
|
177
|
+
res.end(JSON.stringify({
|
|
178
|
+
success: true,
|
|
179
|
+
indexDir,
|
|
180
|
+
indexes,
|
|
181
|
+
summary: {
|
|
182
|
+
totalProjects: indexes.length,
|
|
183
|
+
totalSize,
|
|
184
|
+
totalSizeFormatted: formatSize(totalSize),
|
|
185
|
+
vectorIndexCount,
|
|
186
|
+
normalIndexCount,
|
|
187
|
+
...statusSummary
|
|
188
|
+
}
|
|
189
|
+
}));
|
|
190
|
+
}
|
|
191
|
+
catch (err) {
|
|
192
|
+
res.writeHead(500, { 'Content-Type': 'application/json' });
|
|
193
|
+
res.end(JSON.stringify({ success: false, error: err.message }));
|
|
194
|
+
}
|
|
195
|
+
return true;
|
|
196
|
+
}
|
|
197
|
+
// API: CodexLens Status
|
|
198
|
+
if (pathname === '/api/codexlens/status') {
|
|
199
|
+
const status = await checkVenvStatus();
|
|
200
|
+
res.writeHead(200, { 'Content-Type': 'application/json' });
|
|
201
|
+
res.end(JSON.stringify(status));
|
|
202
|
+
return true;
|
|
203
|
+
}
|
|
204
|
+
// API: CodexLens Bootstrap (Install)
|
|
205
|
+
if (pathname === '/api/codexlens/bootstrap' && req.method === 'POST') {
|
|
206
|
+
handlePostRequest(req, res, async () => {
|
|
207
|
+
try {
|
|
208
|
+
const result = await bootstrapVenv();
|
|
209
|
+
if (result.success) {
|
|
210
|
+
const status = await checkVenvStatus();
|
|
211
|
+
// Broadcast installation event
|
|
212
|
+
broadcastToClients({
|
|
213
|
+
type: 'CODEXLENS_INSTALLED',
|
|
214
|
+
payload: { version: status.version, timestamp: new Date().toISOString() }
|
|
215
|
+
});
|
|
216
|
+
return { success: true, message: 'CodexLens installed successfully', version: status.version };
|
|
217
|
+
}
|
|
218
|
+
else {
|
|
219
|
+
return { success: false, error: result.error, status: 500 };
|
|
220
|
+
}
|
|
221
|
+
}
|
|
222
|
+
catch (err) {
|
|
223
|
+
return { success: false, error: err.message, status: 500 };
|
|
224
|
+
}
|
|
225
|
+
});
|
|
226
|
+
return true;
|
|
227
|
+
}
|
|
228
|
+
// API: CodexLens Uninstall
|
|
229
|
+
if (pathname === '/api/codexlens/uninstall' && req.method === 'POST') {
|
|
230
|
+
handlePostRequest(req, res, async () => {
|
|
231
|
+
try {
|
|
232
|
+
const result = await uninstallCodexLens();
|
|
233
|
+
if (result.success) {
|
|
234
|
+
// Broadcast uninstallation event
|
|
235
|
+
broadcastToClients({
|
|
236
|
+
type: 'CODEXLENS_UNINSTALLED',
|
|
237
|
+
payload: { timestamp: new Date().toISOString() }
|
|
238
|
+
});
|
|
239
|
+
return { success: true, message: 'CodexLens uninstalled successfully' };
|
|
240
|
+
}
|
|
241
|
+
else {
|
|
242
|
+
return { success: false, error: result.error, status: 500 };
|
|
243
|
+
}
|
|
244
|
+
}
|
|
245
|
+
catch (err) {
|
|
246
|
+
return { success: false, error: err.message, status: 500 };
|
|
247
|
+
}
|
|
248
|
+
});
|
|
249
|
+
return true;
|
|
250
|
+
}
|
|
251
|
+
// API: CodexLens Config - GET (Get current configuration with index count)
|
|
252
|
+
if (pathname === '/api/codexlens/config' && req.method === 'GET') {
|
|
253
|
+
try {
|
|
254
|
+
// Fetch both config and status to merge index_count
|
|
255
|
+
const [configResult, statusResult] = await Promise.all([
|
|
256
|
+
executeCodexLens(['config', '--json']),
|
|
257
|
+
executeCodexLens(['status', '--json'])
|
|
258
|
+
]);
|
|
259
|
+
let responseData = { index_dir: '~/.codexlens/indexes', index_count: 0 };
|
|
260
|
+
// Parse config (extract JSON from output that may contain log messages)
|
|
261
|
+
if (configResult.success) {
|
|
262
|
+
try {
|
|
263
|
+
const config = extractJSON(configResult.output);
|
|
264
|
+
if (config.success && config.result) {
|
|
265
|
+
// CLI returns index_dir (not index_root)
|
|
266
|
+
responseData.index_dir = config.result.index_dir || config.result.index_root || responseData.index_dir;
|
|
267
|
+
}
|
|
268
|
+
}
|
|
269
|
+
catch (e) {
|
|
270
|
+
console.error('[CodexLens] Failed to parse config:', e.message);
|
|
271
|
+
console.error('[CodexLens] Config output:', configResult.output.substring(0, 200));
|
|
272
|
+
}
|
|
273
|
+
}
|
|
274
|
+
// Parse status to get index_count (projects_count)
|
|
275
|
+
if (statusResult.success) {
|
|
276
|
+
try {
|
|
277
|
+
const status = extractJSON(statusResult.output);
|
|
278
|
+
if (status.success && status.result) {
|
|
279
|
+
responseData.index_count = status.result.projects_count || 0;
|
|
280
|
+
}
|
|
281
|
+
}
|
|
282
|
+
catch (e) {
|
|
283
|
+
console.error('[CodexLens] Failed to parse status:', e.message);
|
|
284
|
+
console.error('[CodexLens] Status output:', statusResult.output.substring(0, 200));
|
|
285
|
+
}
|
|
286
|
+
}
|
|
287
|
+
res.writeHead(200, { 'Content-Type': 'application/json' });
|
|
288
|
+
res.end(JSON.stringify(responseData));
|
|
289
|
+
}
|
|
290
|
+
catch (err) {
|
|
291
|
+
res.writeHead(500, { 'Content-Type': 'application/json' });
|
|
292
|
+
res.end(JSON.stringify({ error: err.message }));
|
|
293
|
+
}
|
|
294
|
+
return true;
|
|
295
|
+
}
|
|
296
|
+
// API: CodexLens Config - POST (Set configuration)
|
|
297
|
+
if (pathname === '/api/codexlens/config' && req.method === 'POST') {
|
|
298
|
+
handlePostRequest(req, res, async (body) => {
|
|
299
|
+
const { index_dir } = body;
|
|
300
|
+
if (!index_dir) {
|
|
301
|
+
return { success: false, error: 'index_dir is required', status: 400 };
|
|
302
|
+
}
|
|
303
|
+
try {
|
|
304
|
+
const result = await executeCodexLens(['config-set', '--key', 'index_dir', '--value', index_dir, '--json']);
|
|
305
|
+
if (result.success) {
|
|
306
|
+
return { success: true, message: 'Configuration updated successfully' };
|
|
307
|
+
}
|
|
308
|
+
else {
|
|
309
|
+
return { success: false, error: result.error || 'Failed to update configuration', status: 500 };
|
|
310
|
+
}
|
|
311
|
+
}
|
|
312
|
+
catch (err) {
|
|
313
|
+
return { success: false, error: err.message, status: 500 };
|
|
314
|
+
}
|
|
315
|
+
});
|
|
316
|
+
return true;
|
|
317
|
+
}
|
|
318
|
+
// API: CodexLens Clean (Clean indexes)
|
|
319
|
+
if (pathname === '/api/codexlens/clean' && req.method === 'POST') {
|
|
320
|
+
handlePostRequest(req, res, async (body) => {
|
|
321
|
+
const { all = false, path } = body;
|
|
322
|
+
try {
|
|
323
|
+
const args = ['clean'];
|
|
324
|
+
if (all) {
|
|
325
|
+
args.push('--all');
|
|
326
|
+
}
|
|
327
|
+
else if (path) {
|
|
328
|
+
// Path is passed as a positional argument, not as a flag
|
|
329
|
+
args.push(path);
|
|
330
|
+
}
|
|
331
|
+
args.push('--json');
|
|
332
|
+
const result = await executeCodexLens(args);
|
|
333
|
+
if (result.success) {
|
|
334
|
+
return { success: true, message: 'Indexes cleaned successfully' };
|
|
335
|
+
}
|
|
336
|
+
else {
|
|
337
|
+
return { success: false, error: result.error || 'Failed to clean indexes', status: 500 };
|
|
338
|
+
}
|
|
339
|
+
}
|
|
340
|
+
catch (err) {
|
|
341
|
+
return { success: false, error: err.message, status: 500 };
|
|
342
|
+
}
|
|
343
|
+
});
|
|
344
|
+
return true;
|
|
345
|
+
}
|
|
346
|
+
// API: CodexLens Init (Initialize workspace index)
|
|
347
|
+
if (pathname === '/api/codexlens/init' && req.method === 'POST') {
|
|
348
|
+
handlePostRequest(req, res, async (body) => {
|
|
349
|
+
const { path: projectPath, indexType = 'vector', embeddingModel = 'code' } = body;
|
|
350
|
+
const targetPath = projectPath || initialPath;
|
|
351
|
+
// Build CLI arguments based on index type
|
|
352
|
+
const args = ['init', targetPath, '--json'];
|
|
353
|
+
if (indexType === 'normal') {
|
|
354
|
+
args.push('--no-embeddings');
|
|
355
|
+
}
|
|
356
|
+
else {
|
|
357
|
+
// Add embedding model selection for vector index
|
|
358
|
+
args.push('--embedding-model', embeddingModel);
|
|
359
|
+
}
|
|
360
|
+
// Broadcast start event
|
|
361
|
+
broadcastToClients({
|
|
362
|
+
type: 'CODEXLENS_INDEX_PROGRESS',
|
|
363
|
+
payload: { stage: 'start', message: 'Starting index...', percent: 0, path: targetPath, indexType }
|
|
364
|
+
});
|
|
365
|
+
try {
|
|
366
|
+
const result = await executeCodexLens(args, {
|
|
367
|
+
cwd: targetPath,
|
|
368
|
+
timeout: 1800000, // 30 minutes for large codebases
|
|
369
|
+
onProgress: (progress) => {
|
|
370
|
+
// Broadcast progress to all connected clients
|
|
371
|
+
broadcastToClients({
|
|
372
|
+
type: 'CODEXLENS_INDEX_PROGRESS',
|
|
373
|
+
payload: { ...progress, path: targetPath }
|
|
374
|
+
});
|
|
375
|
+
}
|
|
376
|
+
});
|
|
377
|
+
if (result.success) {
|
|
378
|
+
// Broadcast completion
|
|
379
|
+
broadcastToClients({
|
|
380
|
+
type: 'CODEXLENS_INDEX_PROGRESS',
|
|
381
|
+
payload: { stage: 'complete', message: 'Index complete', percent: 100, path: targetPath }
|
|
382
|
+
});
|
|
383
|
+
try {
|
|
384
|
+
const parsed = extractJSON(result.output);
|
|
385
|
+
return { success: true, result: parsed };
|
|
386
|
+
}
|
|
387
|
+
catch {
|
|
388
|
+
return { success: true, output: result.output };
|
|
389
|
+
}
|
|
390
|
+
}
|
|
391
|
+
else {
|
|
392
|
+
// Broadcast error
|
|
393
|
+
broadcastToClients({
|
|
394
|
+
type: 'CODEXLENS_INDEX_PROGRESS',
|
|
395
|
+
payload: { stage: 'error', message: result.error || 'Unknown error', percent: 0, path: targetPath }
|
|
396
|
+
});
|
|
397
|
+
return { success: false, error: result.error, status: 500 };
|
|
398
|
+
}
|
|
399
|
+
}
|
|
400
|
+
catch (err) {
|
|
401
|
+
// Broadcast error
|
|
402
|
+
broadcastToClients({
|
|
403
|
+
type: 'CODEXLENS_INDEX_PROGRESS',
|
|
404
|
+
payload: { stage: 'error', message: err.message, percent: 0, path: targetPath }
|
|
405
|
+
});
|
|
406
|
+
return { success: false, error: err.message, status: 500 };
|
|
407
|
+
}
|
|
408
|
+
});
|
|
409
|
+
return true;
|
|
410
|
+
}
|
|
411
|
+
// API: Cancel CodexLens Indexing
|
|
412
|
+
if (pathname === '/api/codexlens/cancel' && req.method === 'POST') {
|
|
413
|
+
const result = cancelIndexing();
|
|
414
|
+
// Broadcast cancellation event
|
|
415
|
+
if (result.success) {
|
|
416
|
+
broadcastToClients({
|
|
417
|
+
type: 'CODEXLENS_INDEX_PROGRESS',
|
|
418
|
+
payload: { stage: 'cancelled', message: 'Indexing cancelled by user', percent: 0 }
|
|
419
|
+
});
|
|
420
|
+
}
|
|
421
|
+
res.writeHead(result.success ? 200 : 400, { 'Content-Type': 'application/json' });
|
|
422
|
+
res.end(JSON.stringify(result));
|
|
423
|
+
return true;
|
|
424
|
+
}
|
|
425
|
+
// API: Check if indexing is in progress
|
|
426
|
+
if (pathname === '/api/codexlens/indexing-status') {
|
|
427
|
+
const inProgress = isIndexingInProgress();
|
|
428
|
+
res.writeHead(200, { 'Content-Type': 'application/json' });
|
|
429
|
+
res.end(JSON.stringify({ success: true, inProgress }));
|
|
430
|
+
return true;
|
|
431
|
+
}
|
|
432
|
+
// API: CodexLens Semantic Search Status
|
|
433
|
+
if (pathname === '/api/codexlens/semantic/status') {
|
|
434
|
+
const status = await checkSemanticStatus();
|
|
435
|
+
res.writeHead(200, { 'Content-Type': 'application/json' });
|
|
436
|
+
res.end(JSON.stringify(status));
|
|
437
|
+
return true;
|
|
438
|
+
}
|
|
439
|
+
// API: CodexLens Semantic Metadata List
|
|
440
|
+
if (pathname === '/api/codexlens/semantic/metadata') {
|
|
441
|
+
const offset = parseInt(url.searchParams.get('offset') || '0', 10);
|
|
442
|
+
const limit = parseInt(url.searchParams.get('limit') || '50', 10);
|
|
443
|
+
const tool = url.searchParams.get('tool') || '';
|
|
444
|
+
const projectPath = url.searchParams.get('path') || initialPath;
|
|
445
|
+
try {
|
|
446
|
+
const args = [
|
|
447
|
+
'semantic-list',
|
|
448
|
+
'--path', projectPath,
|
|
449
|
+
'--offset', offset.toString(),
|
|
450
|
+
'--limit', limit.toString(),
|
|
451
|
+
'--json'
|
|
452
|
+
];
|
|
453
|
+
if (tool) {
|
|
454
|
+
args.push('--tool', tool);
|
|
455
|
+
}
|
|
456
|
+
const result = await executeCodexLens(args, { cwd: projectPath });
|
|
457
|
+
if (result.success) {
|
|
458
|
+
res.writeHead(200, { 'Content-Type': 'application/json' });
|
|
459
|
+
res.end(result.output);
|
|
460
|
+
}
|
|
461
|
+
else {
|
|
462
|
+
res.writeHead(500, { 'Content-Type': 'application/json' });
|
|
463
|
+
res.end(JSON.stringify({ success: false, error: result.error }));
|
|
464
|
+
}
|
|
465
|
+
}
|
|
466
|
+
catch (err) {
|
|
467
|
+
res.writeHead(500, { 'Content-Type': 'application/json' });
|
|
468
|
+
res.end(JSON.stringify({ success: false, error: err.message }));
|
|
469
|
+
}
|
|
470
|
+
return true;
|
|
471
|
+
}
|
|
472
|
+
// API: CodexLens LLM Enhancement (run enhance command)
|
|
473
|
+
if (pathname === '/api/codexlens/enhance' && req.method === 'POST') {
|
|
474
|
+
handlePostRequest(req, res, async (body) => {
|
|
475
|
+
const { path: projectPath, tool = 'gemini', batchSize = 5, timeoutMs = 300000 } = body;
|
|
476
|
+
const targetPath = projectPath || initialPath;
|
|
477
|
+
try {
|
|
478
|
+
const args = ['enhance', targetPath, '--tool', tool, '--batch-size', batchSize.toString()];
|
|
479
|
+
const result = await executeCodexLens(args, { cwd: targetPath, timeout: timeoutMs + 30000 });
|
|
480
|
+
if (result.success) {
|
|
481
|
+
try {
|
|
482
|
+
const parsed = extractJSON(result.output);
|
|
483
|
+
return { success: true, result: parsed };
|
|
484
|
+
}
|
|
485
|
+
catch {
|
|
486
|
+
return { success: true, output: result.output };
|
|
487
|
+
}
|
|
488
|
+
}
|
|
489
|
+
else {
|
|
490
|
+
return { success: false, error: result.error, status: 500 };
|
|
491
|
+
}
|
|
492
|
+
}
|
|
493
|
+
catch (err) {
|
|
494
|
+
return { success: false, error: err.message, status: 500 };
|
|
495
|
+
}
|
|
496
|
+
});
|
|
497
|
+
return true;
|
|
498
|
+
}
|
|
499
|
+
// API: CodexLens Search (FTS5 text search with mode support)
|
|
500
|
+
if (pathname === '/api/codexlens/search') {
|
|
501
|
+
const query = url.searchParams.get('query') || '';
|
|
502
|
+
const limit = parseInt(url.searchParams.get('limit') || '20', 10);
|
|
503
|
+
const mode = url.searchParams.get('mode') || 'exact'; // exact, fuzzy, hybrid, vector
|
|
504
|
+
const projectPath = url.searchParams.get('path') || initialPath;
|
|
505
|
+
if (!query) {
|
|
506
|
+
res.writeHead(400, { 'Content-Type': 'application/json' });
|
|
507
|
+
res.end(JSON.stringify({ success: false, error: 'Query parameter is required' }));
|
|
508
|
+
return true;
|
|
509
|
+
}
|
|
510
|
+
try {
|
|
511
|
+
const args = ['search', query, '--path', projectPath, '--limit', limit.toString(), '--mode', mode, '--json'];
|
|
512
|
+
const result = await executeCodexLens(args, { cwd: projectPath });
|
|
513
|
+
if (result.success) {
|
|
514
|
+
try {
|
|
515
|
+
const parsed = extractJSON(result.output);
|
|
516
|
+
res.writeHead(200, { 'Content-Type': 'application/json' });
|
|
517
|
+
res.end(JSON.stringify({ success: true, ...parsed.result }));
|
|
518
|
+
}
|
|
519
|
+
catch {
|
|
520
|
+
res.writeHead(200, { 'Content-Type': 'application/json' });
|
|
521
|
+
res.end(JSON.stringify({ success: true, results: [], output: result.output }));
|
|
522
|
+
}
|
|
523
|
+
}
|
|
524
|
+
else {
|
|
525
|
+
res.writeHead(500, { 'Content-Type': 'application/json' });
|
|
526
|
+
res.end(JSON.stringify({ success: false, error: result.error }));
|
|
527
|
+
}
|
|
528
|
+
}
|
|
529
|
+
catch (err) {
|
|
530
|
+
res.writeHead(500, { 'Content-Type': 'application/json' });
|
|
531
|
+
res.end(JSON.stringify({ success: false, error: err.message }));
|
|
532
|
+
}
|
|
533
|
+
return true;
|
|
534
|
+
}
|
|
535
|
+
// API: CodexLens Search Files Only (return file paths only, with mode support)
|
|
536
|
+
if (pathname === '/api/codexlens/search_files') {
|
|
537
|
+
const query = url.searchParams.get('query') || '';
|
|
538
|
+
const limit = parseInt(url.searchParams.get('limit') || '20', 10);
|
|
539
|
+
const mode = url.searchParams.get('mode') || 'exact'; // exact, fuzzy, hybrid, vector
|
|
540
|
+
const projectPath = url.searchParams.get('path') || initialPath;
|
|
541
|
+
if (!query) {
|
|
542
|
+
res.writeHead(400, { 'Content-Type': 'application/json' });
|
|
543
|
+
res.end(JSON.stringify({ success: false, error: 'Query parameter is required' }));
|
|
544
|
+
return true;
|
|
545
|
+
}
|
|
546
|
+
try {
|
|
547
|
+
const args = ['search', query, '--path', projectPath, '--limit', limit.toString(), '--mode', mode, '--files-only', '--json'];
|
|
548
|
+
const result = await executeCodexLens(args, { cwd: projectPath });
|
|
549
|
+
if (result.success) {
|
|
550
|
+
try {
|
|
551
|
+
const parsed = extractJSON(result.output);
|
|
552
|
+
res.writeHead(200, { 'Content-Type': 'application/json' });
|
|
553
|
+
res.end(JSON.stringify({ success: true, ...parsed.result }));
|
|
554
|
+
}
|
|
555
|
+
catch {
|
|
556
|
+
res.writeHead(200, { 'Content-Type': 'application/json' });
|
|
557
|
+
res.end(JSON.stringify({ success: true, files: [], output: result.output }));
|
|
558
|
+
}
|
|
559
|
+
}
|
|
560
|
+
else {
|
|
561
|
+
res.writeHead(500, { 'Content-Type': 'application/json' });
|
|
562
|
+
res.end(JSON.stringify({ success: false, error: result.error }));
|
|
563
|
+
}
|
|
564
|
+
}
|
|
565
|
+
catch (err) {
|
|
566
|
+
res.writeHead(500, { 'Content-Type': 'application/json' });
|
|
567
|
+
res.end(JSON.stringify({ success: false, error: err.message }));
|
|
568
|
+
}
|
|
569
|
+
return true;
|
|
570
|
+
}
|
|
571
|
+
// API: CodexLens Symbol Search (search for symbols by name)
|
|
572
|
+
if (pathname === '/api/codexlens/symbol') {
|
|
573
|
+
const query = url.searchParams.get('query') || '';
|
|
574
|
+
const file = url.searchParams.get('file');
|
|
575
|
+
const limit = parseInt(url.searchParams.get('limit') || '20', 10);
|
|
576
|
+
const projectPath = url.searchParams.get('path') || initialPath;
|
|
577
|
+
if (!query && !file) {
|
|
578
|
+
res.writeHead(400, { 'Content-Type': 'application/json' });
|
|
579
|
+
res.end(JSON.stringify({ success: false, error: 'Either query or file parameter is required' }));
|
|
580
|
+
return true;
|
|
581
|
+
}
|
|
582
|
+
try {
|
|
583
|
+
let args;
|
|
584
|
+
if (file) {
|
|
585
|
+
// Get symbols from a specific file
|
|
586
|
+
args = ['symbol', '--file', file, '--json'];
|
|
587
|
+
}
|
|
588
|
+
else {
|
|
589
|
+
// Search for symbols by name
|
|
590
|
+
args = ['symbol', query, '--path', projectPath, '--limit', limit.toString(), '--json'];
|
|
591
|
+
}
|
|
592
|
+
const result = await executeCodexLens(args, { cwd: projectPath });
|
|
593
|
+
if (result.success) {
|
|
594
|
+
try {
|
|
595
|
+
const parsed = extractJSON(result.output);
|
|
596
|
+
res.writeHead(200, { 'Content-Type': 'application/json' });
|
|
597
|
+
res.end(JSON.stringify({ success: true, ...parsed.result }));
|
|
598
|
+
}
|
|
599
|
+
catch {
|
|
600
|
+
res.writeHead(200, { 'Content-Type': 'application/json' });
|
|
601
|
+
res.end(JSON.stringify({ success: true, symbols: [], output: result.output }));
|
|
602
|
+
}
|
|
603
|
+
}
|
|
604
|
+
else {
|
|
605
|
+
res.writeHead(500, { 'Content-Type': 'application/json' });
|
|
606
|
+
res.end(JSON.stringify({ success: false, error: result.error }));
|
|
607
|
+
}
|
|
608
|
+
}
|
|
609
|
+
catch (err) {
|
|
610
|
+
res.writeHead(500, { 'Content-Type': 'application/json' });
|
|
611
|
+
res.end(JSON.stringify({ success: false, error: err.message }));
|
|
612
|
+
}
|
|
613
|
+
return true;
|
|
614
|
+
}
|
|
615
|
+
// API: CodexLens Semantic Search Install (fastembed, ONNX-based, ~200MB)
|
|
616
|
+
if (pathname === '/api/codexlens/semantic/install' && req.method === 'POST') {
|
|
617
|
+
handlePostRequest(req, res, async () => {
|
|
618
|
+
try {
|
|
619
|
+
const result = await installSemantic();
|
|
620
|
+
if (result.success) {
|
|
621
|
+
const status = await checkSemanticStatus();
|
|
622
|
+
return {
|
|
623
|
+
success: true,
|
|
624
|
+
message: 'Semantic search installed successfully (fastembed)',
|
|
625
|
+
...status
|
|
626
|
+
};
|
|
627
|
+
}
|
|
628
|
+
else {
|
|
629
|
+
return { success: false, error: result.error, status: 500 };
|
|
630
|
+
}
|
|
631
|
+
}
|
|
632
|
+
catch (err) {
|
|
633
|
+
return { success: false, error: err.message, status: 500 };
|
|
634
|
+
}
|
|
635
|
+
});
|
|
636
|
+
return true;
|
|
637
|
+
}
|
|
638
|
+
// API: CodexLens Model List (list available embedding models)
|
|
639
|
+
if (pathname === '/api/codexlens/models' && req.method === 'GET') {
|
|
640
|
+
try {
|
|
641
|
+
const result = await executeCodexLens(['model-list', '--json']);
|
|
642
|
+
if (result.success) {
|
|
643
|
+
try {
|
|
644
|
+
const parsed = extractJSON(result.output);
|
|
645
|
+
res.writeHead(200, { 'Content-Type': 'application/json' });
|
|
646
|
+
res.end(JSON.stringify(parsed));
|
|
647
|
+
}
|
|
648
|
+
catch {
|
|
649
|
+
res.writeHead(200, { 'Content-Type': 'application/json' });
|
|
650
|
+
res.end(JSON.stringify({ success: true, result: { models: [] }, output: result.output }));
|
|
651
|
+
}
|
|
652
|
+
}
|
|
653
|
+
else {
|
|
654
|
+
res.writeHead(500, { 'Content-Type': 'application/json' });
|
|
655
|
+
res.end(JSON.stringify({ success: false, error: result.error }));
|
|
656
|
+
}
|
|
657
|
+
}
|
|
658
|
+
catch (err) {
|
|
659
|
+
res.writeHead(500, { 'Content-Type': 'application/json' });
|
|
660
|
+
res.end(JSON.stringify({ success: false, error: err.message }));
|
|
661
|
+
}
|
|
662
|
+
return true;
|
|
663
|
+
}
|
|
664
|
+
// API: CodexLens Model Download (download embedding model by profile)
|
|
665
|
+
if (pathname === '/api/codexlens/models/download' && req.method === 'POST') {
|
|
666
|
+
handlePostRequest(req, res, async (body) => {
|
|
667
|
+
const { profile } = body;
|
|
668
|
+
if (!profile) {
|
|
669
|
+
return { success: false, error: 'profile is required', status: 400 };
|
|
670
|
+
}
|
|
671
|
+
try {
|
|
672
|
+
const result = await executeCodexLens(['model-download', profile, '--json'], { timeout: 600000 }); // 10 min for download
|
|
673
|
+
if (result.success) {
|
|
674
|
+
try {
|
|
675
|
+
const parsed = extractJSON(result.output);
|
|
676
|
+
return { success: true, ...parsed };
|
|
677
|
+
}
|
|
678
|
+
catch {
|
|
679
|
+
return { success: true, output: result.output };
|
|
680
|
+
}
|
|
681
|
+
}
|
|
682
|
+
else {
|
|
683
|
+
return { success: false, error: result.error, status: 500 };
|
|
684
|
+
}
|
|
685
|
+
}
|
|
686
|
+
catch (err) {
|
|
687
|
+
return { success: false, error: err.message, status: 500 };
|
|
688
|
+
}
|
|
689
|
+
});
|
|
690
|
+
return true;
|
|
691
|
+
}
|
|
692
|
+
// API: CodexLens Model Delete (delete embedding model by profile)
|
|
693
|
+
if (pathname === '/api/codexlens/models/delete' && req.method === 'POST') {
|
|
694
|
+
handlePostRequest(req, res, async (body) => {
|
|
695
|
+
const { profile } = body;
|
|
696
|
+
if (!profile) {
|
|
697
|
+
return { success: false, error: 'profile is required', status: 400 };
|
|
698
|
+
}
|
|
699
|
+
try {
|
|
700
|
+
const result = await executeCodexLens(['model-delete', profile, '--json']);
|
|
701
|
+
if (result.success) {
|
|
702
|
+
try {
|
|
703
|
+
const parsed = extractJSON(result.output);
|
|
704
|
+
return { success: true, ...parsed };
|
|
705
|
+
}
|
|
706
|
+
catch {
|
|
707
|
+
return { success: true, output: result.output };
|
|
708
|
+
}
|
|
709
|
+
}
|
|
710
|
+
else {
|
|
711
|
+
return { success: false, error: result.error, status: 500 };
|
|
712
|
+
}
|
|
713
|
+
}
|
|
714
|
+
catch (err) {
|
|
715
|
+
return { success: false, error: err.message, status: 500 };
|
|
716
|
+
}
|
|
717
|
+
});
|
|
718
|
+
return true;
|
|
719
|
+
}
|
|
720
|
+
// API: CodexLens Model Info (get model info by profile)
|
|
721
|
+
if (pathname === '/api/codexlens/models/info' && req.method === 'GET') {
|
|
722
|
+
const profile = url.searchParams.get('profile');
|
|
723
|
+
if (!profile) {
|
|
724
|
+
res.writeHead(400, { 'Content-Type': 'application/json' });
|
|
725
|
+
res.end(JSON.stringify({ success: false, error: 'profile parameter is required' }));
|
|
726
|
+
return true;
|
|
727
|
+
}
|
|
728
|
+
try {
|
|
729
|
+
const result = await executeCodexLens(['model-info', profile, '--json']);
|
|
730
|
+
if (result.success) {
|
|
731
|
+
try {
|
|
732
|
+
const parsed = extractJSON(result.output);
|
|
733
|
+
res.writeHead(200, { 'Content-Type': 'application/json' });
|
|
734
|
+
res.end(JSON.stringify(parsed));
|
|
735
|
+
}
|
|
736
|
+
catch {
|
|
737
|
+
res.writeHead(200, { 'Content-Type': 'application/json' });
|
|
738
|
+
res.end(JSON.stringify({ success: false, error: 'Failed to parse response' }));
|
|
739
|
+
}
|
|
740
|
+
}
|
|
741
|
+
else {
|
|
742
|
+
res.writeHead(500, { 'Content-Type': 'application/json' });
|
|
743
|
+
res.end(JSON.stringify({ success: false, error: result.error }));
|
|
744
|
+
}
|
|
745
|
+
}
|
|
746
|
+
catch (err) {
|
|
747
|
+
res.writeHead(500, { 'Content-Type': 'application/json' });
|
|
748
|
+
res.end(JSON.stringify({ success: false, error: err.message }));
|
|
749
|
+
}
|
|
750
|
+
return true;
|
|
751
|
+
}
|
|
752
|
+
return false;
|
|
753
|
+
}
|
|
754
|
+
//# sourceMappingURL=codexlens-routes.js.map
|