oh-my-opencode 5.0.0-beta.6 → 5.0.0-beta.60
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/.agents/command/publish.md +59 -23
- package/.agents/skills/codex-qa/scripts/lsp-e2e.sh +1 -3
- package/.agents/skills/opencode-qa/scripts/lsp-e2e.sh +1 -1
- package/.agents/skills/pre-publish-review/SKILL.md +9 -12
- package/.agents/skills/publish/SKILL.md +59 -23
- package/.agents/skills/senpi-qa/SKILL.md +80 -0
- package/.agents/skills/senpi-qa/scripts/resolve-evidence-dir.mjs +65 -0
- package/.agents/skills/senpi-qa/scripts/resolve-evidence-dir.test.mjs +171 -0
- package/.agents/skills/tech-debt-audit/SKILL.md +6 -76
- package/.agents/skills/work-with-pr/SKILL.md +37 -23
- package/.opencode/command/publish.md +59 -23
- package/.opencode/skills/pre-publish-review/SKILL.md +9 -12
- package/.opencode/skills/work-with-pr/SKILL.md +37 -23
- package/README.ja.md +65 -60
- package/README.ko.md +66 -61
- package/README.md +65 -72
- package/README.ru.md +62 -60
- package/README.zh-cn.md +61 -60
- package/THIRD-PARTY-NOTICES.md +27 -99
- package/dist/agents/atlas/agent.d.ts +0 -1
- package/dist/agents/gpt-prompt-identity.d.ts +1 -1
- package/dist/agents/sisyphus/grok-4.d.ts +20 -0
- package/dist/agents/sisyphus/index.d.ts +2 -0
- package/dist/agents/sisyphus-agent-config.d.ts +6 -0
- package/dist/agents/sisyphus-agent-factory.d.ts +1 -1
- package/dist/agents/sisyphus-runtime-prompt-reconciler.d.ts +15 -4
- package/dist/agents/types.d.ts +4 -2
- package/dist/cli/config-manager/parse-opencode-config-file.d.ts +2 -1
- package/dist/cli/doctor/checks/index.d.ts +2 -0
- package/dist/cli/doctor/checks/latest-version.d.ts +11 -0
- package/dist/cli/doctor/checks/system-plugin.d.ts +4 -3
- package/dist/cli/doctor/framework/constants.d.ts +5 -0
- package/dist/cli/doctor/framework/types.d.ts +2 -0
- package/dist/cli/fallback-lane-policy.d.ts +1 -0
- package/dist/cli/index.js +51738 -59690
- package/dist/cli/install-codex/install-codex-test-fixtures.d.ts +1 -1
- package/dist/cli/run/on-complete-hook.d.ts +2 -0
- package/dist/cli/runtime-commands.d.ts +1 -1
- package/dist/cli/worktree-sweep/classify.d.ts +16 -0
- package/dist/cli/worktree-sweep/format.d.ts +8 -0
- package/dist/cli/worktree-sweep/git.d.ts +19 -0
- package/dist/cli/worktree-sweep/index.d.ts +7 -0
- package/dist/cli/worktree-sweep/options.d.ts +2 -0
- package/dist/cli/worktree-sweep/parse-worktree-list.d.ts +8 -0
- package/dist/cli/worktree-sweep/sweep.d.ts +2 -0
- package/dist/cli/worktree-sweep/types.d.ts +65 -0
- package/dist/cli/worktree-sweep/worktree-sweep.d.ts +2 -0
- package/dist/cli-node/index.js +50900 -58829
- package/dist/config/index.d.ts +1 -1
- package/dist/config/schema/background-task.d.ts +1 -0
- package/dist/config/schema/commands.d.ts +1 -1
- package/dist/config/schema/hooks.d.ts +1 -2
- package/dist/config/schema/oh-my-opencode-config.d.ts +5 -11
- package/dist/config/schema/ulw-execute.d.ts +5 -0
- package/dist/config/schema.d.ts +0 -1
- package/dist/config/validate.d.ts +2 -0
- package/dist/create-hooks.d.ts +3 -2
- package/dist/features/background-agent/compaction-aware-message-resolver.d.ts +1 -0
- package/dist/features/background-agent/constants.d.ts +0 -7
- package/dist/features/background-agent/error-classifier.d.ts +1 -0
- package/dist/features/background-agent/manager.d.ts +9 -1
- package/dist/features/background-agent/parent-wake-dispatched-tracker.d.ts +0 -1
- package/dist/features/background-agent/parent-wake-notifier-types.d.ts +1 -1
- package/dist/features/background-agent/parent-wake-prompt-dispatch.d.ts +1 -1
- package/dist/features/background-agent/parent-wake-session-inspector.d.ts +1 -1
- package/dist/features/background-agent/subagent-spawn-limits.d.ts +8 -0
- package/dist/features/background-agent/types.d.ts +4 -0
- package/dist/features/btw-side/btw-command-draft.d.ts +7 -0
- package/dist/features/btw-side/context-injector.d.ts +15 -0
- package/dist/features/btw-side/index.d.ts +8 -0
- package/dist/features/btw-side/metadata.d.ts +15 -0
- package/dist/features/btw-side/parent-context-budget.d.ts +9 -0
- package/dist/features/btw-side/server-session-registry.d.ts +8 -0
- package/dist/features/btw-side/tui-adoption-cache.d.ts +13 -0
- package/dist/features/btw-side/tui-adoption-guard.d.ts +5 -0
- package/dist/features/btw-side/tui-controller-types.d.ts +68 -0
- package/dist/features/btw-side/tui-controller.d.ts +19 -0
- package/dist/features/btw-side/tui-escape-return.d.ts +12 -0
- package/dist/features/btw-side/tui-keymap.d.ts +17 -0
- package/dist/features/btw-side/tui-parent-validator.d.ts +6 -0
- package/dist/features/btw-side/tui-picker-options.d.ts +20 -0
- package/dist/features/btw-side/tui-picker.d.ts +9 -0
- package/dist/features/btw-side/tui-prompt-queue.d.ts +8 -0
- package/dist/features/btw-side/tui-session-bridge.d.ts +11 -0
- package/dist/features/btw-side/tui-session-catalog.d.ts +35 -0
- package/dist/features/btw-side/tui-side-removal.d.ts +11 -0
- package/dist/features/btw-side/tui-side-start.d.ts +9 -0
- package/dist/features/btw-side/tui-wiring.d.ts +8 -0
- package/dist/features/builtin-commands/templates/ulw-execute.d.ts +1 -0
- package/dist/features/builtin-commands/types.d.ts +1 -1
- package/dist/features/claude-tasks/storage.d.ts +7 -2
- package/dist/features/hook-message-injector/index.d.ts +1 -0
- package/dist/features/hook-message-injector/sdk-message-lookup.d.ts +1 -0
- package/dist/features/monitor/manager-internals.d.ts +1 -1
- package/dist/features/monitor/output-injector-types.d.ts +1 -1
- package/dist/features/opengateway-provider/index.d.ts +13 -0
- package/dist/features/task-toast-manager/manager.d.ts +0 -24
- package/dist/features/team-mode/tools/messaging-fallback-wake.d.ts +17 -0
- package/dist/features/team-mode/tools/messaging-live-delivery-recipient.d.ts +3 -0
- package/dist/features/team-mode/tools/messaging-runtime.d.ts +7 -0
- package/dist/hooks/anthropic-context-window-limit-recovery/message-storage-directory.d.ts +0 -3
- package/dist/hooks/anthropic-context-window-limit-recovery/state.d.ts +1 -0
- package/dist/hooks/anthropic-context-window-limit-recovery/storage/empty-messages.d.ts +0 -1
- package/dist/hooks/anthropic-context-window-limit-recovery/tool-result-storage.d.ts +11 -0
- package/dist/hooks/atlas/atlas-hook.d.ts +1 -0
- package/dist/hooks/atlas/atlas-lifecycle-store.d.ts +50 -0
- package/dist/hooks/atlas/event-handler.d.ts +1 -0
- package/dist/hooks/atlas/final-wave-approval-gate.test-support.d.ts +50 -0
- package/dist/hooks/atlas/system-reminder-templates.d.ts +0 -1
- package/dist/hooks/atlas/tool-execute-before.d.ts +3 -0
- package/dist/hooks/atlas/types.d.ts +1 -0
- package/dist/hooks/claude-code-hooks/session-hook-state.d.ts +1 -0
- package/dist/hooks/claude-code-hooks/stop.d.ts +2 -0
- package/dist/hooks/claude-code-hooks/todo.d.ts +0 -1
- package/dist/hooks/claude-code-hooks/transcript.d.ts +2 -0
- package/dist/hooks/compaction-context-injector/validated-model.d.ts +2 -0
- package/dist/hooks/fsync-skip-warning/index.d.ts +4 -0
- package/dist/hooks/hashline-edit-diff-enhancer/hook.d.ts +1 -0
- package/dist/hooks/hashline-edit-diff-enhancer/pending-captures.d.ts +13 -0
- package/dist/hooks/index.d.ts +1 -2
- package/dist/hooks/keyword-detector/hook.d.ts +9 -0
- package/dist/hooks/keyword-detector/ultrawork/index.d.ts +2 -0
- package/dist/hooks/keyword-detector/ultrawork/source-detector.d.ts +0 -1
- package/dist/hooks/model-fallback/hook.d.ts +1 -1
- package/dist/hooks/prometheus-md-only/agent-resolution.d.ts +2 -2
- package/dist/hooks/runtime-fallback/chat-message-handler.d.ts +2 -0
- package/dist/hooks/runtime-fallback/retry-model-payload.d.ts +1 -0
- package/dist/hooks/runtime-fallback/runtime-model-settings.d.ts +6 -0
- package/dist/hooks/runtime-fallback/session-status-handler.d.ts +1 -1
- package/dist/hooks/runtime-fallback/types.d.ts +3 -1
- package/dist/hooks/sisyphus-junior-notepad/constants.d.ts +1 -1
- package/dist/hooks/todo-continuation-enforcer/types.d.ts +1 -0
- package/dist/hooks/{start-work → ulw-execute}/context-info-builder.d.ts +1 -1
- package/dist/hooks/{start-work → ulw-execute}/index.d.ts +1 -1
- package/dist/hooks/ulw-execute/ulw-execute-hook.d.ts +23 -0
- package/dist/hooks/unstable-agent-babysitter/task-message-analyzer.d.ts +1 -0
- package/dist/index.js +29256 -25391
- package/dist/mcp/index.d.ts +0 -4
- package/dist/mcp/types.d.ts +0 -1
- package/dist/oh-my-opencode.schema.json +21 -47
- package/dist/plugin/chat-message/types.d.ts +6 -4
- package/dist/plugin/chat-message/ulw-execute-message.d.ts +5 -0
- package/dist/plugin/event-session-lifecycle.d.ts +1 -0
- package/dist/plugin/hooks/create-core-hooks.d.ts +2 -2
- package/dist/plugin/hooks/create-session-hooks.d.ts +2 -3
- package/dist/plugin/hooks/create-transform-hooks.d.ts +2 -0
- package/dist/plugin/messages-transform.d.ts +1 -0
- package/dist/plugin/stop-continuation.d.ts +3 -0
- package/dist/plugin/system-transform.d.ts +5 -1
- package/dist/plugin-dispose.d.ts +3 -0
- package/dist/shared/agent-tool-restrictions.d.ts +0 -1
- package/dist/shared/compaction-agent-config-checkpoint.d.ts +1 -0
- package/dist/shared/index.d.ts +2 -0
- package/dist/shared/legacy-plugin-warning.d.ts +2 -1
- package/dist/shared/normalize-sdk-response.d.ts +1 -0
- package/dist/shared/omo-process-sweep.d.ts +2 -4
- package/dist/shared/plugin-entry-migrator.d.ts +4 -3
- package/dist/shared/plugin-entry-shape.d.ts +6 -0
- package/dist/shared/runtime-fallback-retry-marker.d.ts +16 -0
- package/dist/shared/shell-env.d.ts +1 -1
- package/dist/skills/ast-grep/AGENTS.md +51 -0
- package/dist/skills/ast-grep/SKILL.md +1 -1
- package/dist/skills/coding-agent-sessions/AGENTS.md +62 -0
- package/dist/skills/coding-agent-sessions/SKILL.md +1 -1
- package/dist/skills/data-scientist/SKILL.md +99 -239
- package/dist/skills/data-scientist/references/execution-surfaces.md +91 -0
- package/dist/skills/data-scientist/references/placement.md +74 -0
- package/dist/skills/data-scientist/references/polars-lane.md +95 -0
- package/dist/skills/data-scientist/references/uv-setup.md +1 -1
- package/dist/skills/data-scientist/references/visualization.md +64 -0
- package/dist/skills/data-scientist/scripts/ensure-js-deps.sh +28 -0
- package/dist/skills/data-scientist/scripts/ensure-py-deps.sh +37 -0
- package/dist/skills/debugging/SKILL.md +3 -1
- package/dist/skills/debugging/references/methodology/00-setup.md +12 -0
- package/dist/skills/debugging/references/methodology/02-investigate.md +21 -0
- package/dist/skills/debugging/references/runtimes/go.md +15 -1
- package/dist/skills/debugging/references/runtimes/native-binary.md +38 -0
- package/dist/skills/debugging/references/runtimes/node.md +25 -0
- package/dist/skills/debugging/references/runtimes/python.md +13 -0
- package/dist/skills/debugging/references/runtimes/rust.md +41 -0
- package/dist/skills/debugging/references/scripts/dap.mjs +267 -0
- package/dist/skills/debugging/references/scripts/dap.test.ts +86 -0
- package/dist/skills/debugging/references/scripts/fixture-adapter.mjs +59 -0
- package/dist/skills/debugging/references/tools/dap.md +103 -0
- package/dist/skills/debugging/references/tools/frida.md +193 -0
- package/dist/skills/frontend/ATTRIBUTION.md +10 -0
- package/dist/skills/frontend/SKILL.md +15 -8
- package/dist/skills/frontend/references/design/README.md +10 -2
- package/dist/skills/frontend/references/design/_INDEX.md +2 -0
- package/dist/skills/frontend/references/design/ambience-skill.md +145 -0
- package/dist/skills/frontend/references/design/interaction-skill.md +2 -0
- package/dist/skills/frontend/references/design/print-paged-media.md +76 -0
- package/dist/skills/frontend/references/design/stylegallery.md +80 -0
- package/dist/skills/frontend/references/designpowers/README.md +1 -1
- package/dist/skills/frontend/references/designpowers/lane-a-direction.md +1 -1
- package/dist/skills/frontend/references/designpowers/lane-b-execution.md +11 -11
- package/dist/skills/frontend/references/designpowers/lane-d-memory.md +3 -3
- package/dist/skills/frontend/references/designpowers/orchestration.md +1 -1
- package/dist/skills/frontend/references/designpowers/routing.md +5 -5
- package/dist/skills/git-master/SKILL.md +1 -1
- package/dist/skills/init-deep/SKILL.md +14 -14
- package/dist/skills/lsp-setup/SKILL.md +1 -1
- package/dist/skills/programming/SKILL.md +1 -1
- package/dist/skills/refactor/SKILL.md +4 -4
- package/dist/skills/remove-ai-slops/SKILL.md +1 -1
- package/dist/skills/review-work/SKILL.md +101 -419
- package/dist/skills/ultimate-browsing/ATTRIBUTION.md +38 -11
- package/dist/skills/ultimate-browsing/SKILL.md +26 -9
- package/dist/skills/ultimate-browsing/engine/AGENTS.md +110 -0
- package/dist/skills/ultimate-browsing/engine/templates/package.json +1 -1
- package/dist/skills/ultimate-browsing/references/chrome-stealth.md +23 -18
- package/dist/skills/ultimate-browsing/references/insane-search/README.md +9 -2
- package/dist/skills/{start-work → ulw-execute}/SKILL.md +20 -19
- package/dist/skills/ulw-plan/SKILL.md +7 -8
- package/dist/skills/ulw-plan/references/full-workflow.md +31 -7
- package/dist/skills/ulw-plan/references/intent-clear.md +2 -1
- package/dist/skills/ulw-plan/references/intent-unclear.md +5 -5
- package/dist/skills/ulw-plan/scripts/scaffold-plan.mjs +1 -1
- package/dist/skills/ulw-research/SKILL.md +8 -3
- package/dist/skills/visual-qa/AGENTS.md +58 -0
- package/dist/skills/visual-qa/SKILL.md +4 -3
- package/dist/tools/delegate-task/builtin-categories.d.ts +3 -1
- package/dist/tools/delegate-task/builtin-category-definition.d.ts +2 -1
- package/dist/tools/delegate-task/constants.d.ts +2 -2
- package/dist/tools/delegate-task/openai-categories.d.ts +7 -2
- package/dist/tools/delegate-task/sync-session-cleanup.d.ts +3 -0
- package/dist/tools/delegate-task/sync-session-poller.d.ts +1 -0
- package/dist/tools/delegate-task/tool-description.d.ts +3 -1
- package/dist/tools/delegate-task/types.d.ts +4 -0
- package/dist/tools/session-manager/directory-filter.d.ts +2 -0
- package/dist/tui.d.ts +12 -0
- package/dist/tui.js +37048 -46599
- package/package.json +47 -41
- package/packages/git-bash-mcp/dist/cli.js +6 -1
- package/packages/git-bash-mcp/package.json +1 -1
- package/packages/lsp-core/src/index.ts +1 -0
- package/packages/lsp-core/src/lsp/client-diagnostics-concurrency.integration.test.ts +44 -0
- package/packages/lsp-core/src/lsp/client-diagnostics-freshness.integration.test.ts +57 -48
- package/packages/lsp-core/src/lsp/client-diagnostics-pull-timeout.test.ts +64 -0
- package/packages/lsp-core/src/lsp/client-wrapper-outside-cwd.test.ts +78 -0
- package/packages/lsp-core/src/lsp/client-wrapper.test.ts +103 -6
- package/packages/lsp-core/src/lsp/client-wrapper.ts +50 -16
- package/packages/lsp-core/src/lsp/client.ts +32 -3
- package/packages/lsp-core/src/lsp/connection.ts +16 -0
- package/packages/lsp-core/src/lsp/constants.ts +6 -0
- package/packages/lsp-core/src/lsp/controlled-clock-test-support.ts +61 -0
- package/packages/lsp-core/src/lsp/errors.ts +15 -0
- package/packages/lsp-core/src/lsp/fixtures/workspace-edit-server.mjs +10 -3
- package/packages/lsp-core/src/lsp/format-document.test.ts +143 -0
- package/packages/lsp-core/src/lsp/format-document.ts +90 -0
- package/packages/lsp-core/src/lsp/json-rpc-connection.ts +11 -6
- package/packages/lsp-core/src/lsp/manager-lifecycle.test.ts +262 -0
- package/packages/lsp-core/src/lsp/manager-max-clients.test.ts +151 -0
- package/packages/lsp-core/src/lsp/manager.ts +138 -12
- package/packages/lsp-core/src/lsp/outside-context-workspace.ts +33 -0
- package/packages/lsp-core/src/lsp/server-definitions.ts +29 -0
- package/packages/lsp-core/src/lsp/server-installation.test.ts +376 -0
- package/packages/lsp-core/src/lsp/server-installation.ts +200 -27
- package/packages/lsp-core/src/lsp/server-resolution-local-binary.test.ts +170 -0
- package/packages/lsp-core/src/lsp/server-resolution.ts +18 -5
- package/packages/lsp-core/src/lsp/timer-provider.ts +13 -0
- package/packages/lsp-core/src/lsp/transport-request-timeout.test.ts +73 -0
- package/packages/lsp-core/src/lsp/transport.ts +16 -2
- package/packages/lsp-core/src/lsp/types.ts +8 -0
- package/packages/lsp-core/src/lsp/workspace-apply-edit-test-support.ts +29 -1
- package/packages/lsp-core/src/lsp/workspace-document-state.test.ts +84 -1
- package/packages/lsp-core/src/lsp/workspace-document-state.ts +30 -11
- package/packages/lsp-core/src/lsp/workspace-markers.ts +18 -0
- package/packages/lsp-core/src/mcp.ts +3 -0
- package/packages/lsp-core/src/request-context.test.ts +29 -0
- package/packages/lsp-core/src/request-context.ts +1 -1
- package/packages/lsp-core/src/tool-surface.test.ts +13 -1
- package/packages/lsp-core/src/tools/definitions.ts +14 -0
- package/packages/lsp-core/src/tools/format.test.ts +56 -0
- package/packages/lsp-core/src/tools/format.ts +56 -0
- package/packages/lsp-core/src/tools/index.ts +1 -0
- package/packages/lsp-core/src/tools/parameters.test.ts +51 -0
- package/packages/lsp-core/src/tools/types.ts +10 -0
- package/packages/lsp-daemon/dist/cli.js +902 -479
- package/packages/lsp-daemon/dist/client.d.ts +10 -0
- package/packages/lsp-daemon/dist/client.js +920 -493
- package/packages/lsp-daemon/dist/daemon-client.d.ts +1 -0
- package/packages/lsp-daemon/dist/daemon-client.js +3 -0
- package/packages/lsp-daemon/dist/ensure-daemon.d.ts +6 -1
- package/packages/lsp-daemon/dist/ensure-daemon.js +10 -2
- package/packages/lsp-daemon/dist/index.js +824 -402
- package/packages/lsp-daemon/dist/ownership.js +2 -2
- package/packages/lsp-daemon/dist/proxy.js +3 -0
- package/packages/lsp-daemon/dist/version-reap.js +1 -1
- package/packages/lsp-daemon/package.json +1 -1
- package/packages/lsp-tools-mcp/dist/cli.js +762 -341
- package/packages/lsp-tools-mcp/dist/lsp/manager.js +272 -138
- package/packages/lsp-tools-mcp/dist/mcp.js +787 -368
- package/packages/lsp-tools-mcp/dist/request-context.js +12 -13
- package/packages/lsp-tools-mcp/dist/tools.js +717 -302
- package/packages/lsp-tools-mcp/package.json +1 -1
- package/packages/omo-codex/THIRD-PARTY-NOTICES.md +4 -21
- package/packages/omo-codex/plugin/.codex-plugin/plugin.json +4 -6
- package/packages/omo-codex/plugin/.mcp.json +0 -6
- package/packages/omo-codex/plugin/AGENTS.md +47 -0
- package/packages/omo-codex/plugin/README.md +6 -2
- package/packages/omo-codex/plugin/components/bootstrap/dist/cli.js +197 -148
- package/packages/omo-codex/plugin/components/bootstrap/hooks/hooks.json +1 -1
- package/packages/omo-codex/plugin/components/bootstrap/package.json +1 -1
- package/packages/omo-codex/plugin/components/bootstrap/src/hook.ts +1 -0
- package/packages/omo-codex/plugin/components/comment-checker/AGENTS.md +9 -0
- package/packages/omo-codex/plugin/components/comment-checker/biome.json +2 -2
- package/packages/omo-codex/plugin/components/comment-checker/dist/cli.js +2 -1
- package/packages/omo-codex/plugin/components/comment-checker/hooks/hooks.json +1 -1
- package/packages/omo-codex/plugin/components/comment-checker/package.json +5 -5
- package/packages/omo-codex/plugin/components/comment-checker/src/apply-patch.ts +2 -8
- package/packages/omo-codex/plugin/components/comment-checker/src/core.ts +1 -2
- package/packages/omo-codex/plugin/components/comment-checker/src/request-extractor.ts +1 -1
- package/packages/omo-codex/plugin/components/comment-checker/src/runner.ts +1 -0
- package/packages/omo-codex/plugin/components/git-bash/AGENTS.md +1 -1
- package/packages/omo-codex/plugin/components/git-bash/dist/cli.js +1 -1
- package/packages/omo-codex/plugin/components/git-bash/dist/codex-hook.js +2 -1
- package/packages/omo-codex/plugin/components/git-bash/hooks/hooks.json +2 -2
- package/packages/omo-codex/plugin/components/git-bash/package.json +3 -4
- package/packages/omo-codex/plugin/components/git-bash/src/codex-hook.ts +2 -1
- package/packages/omo-codex/plugin/components/git-bash/test/codex-hook.test.ts +6 -7
- package/packages/omo-codex/plugin/components/lazycodex-executor-verify/AGENTS.md +2 -2
- package/packages/omo-codex/plugin/components/lazycodex-executor-verify/biome.json +2 -2
- package/packages/omo-codex/plugin/components/lazycodex-executor-verify/directive.md +2 -0
- package/packages/omo-codex/plugin/components/lazycodex-executor-verify/dist/cli.js +36 -29
- package/packages/omo-codex/plugin/components/lazycodex-executor-verify/dist/codex-hook.js +32 -26
- package/packages/omo-codex/plugin/components/lazycodex-executor-verify/dist/types.d.ts +3 -0
- package/packages/omo-codex/plugin/components/lazycodex-executor-verify/hooks/hooks.json +1 -1
- package/packages/omo-codex/plugin/components/lazycodex-executor-verify/package.json +5 -5
- package/packages/omo-codex/plugin/components/lazycodex-executor-verify/src/codex-hook.ts +32 -28
- package/packages/omo-codex/plugin/components/lazycodex-executor-verify/src/types.ts +3 -0
- package/packages/omo-codex/plugin/components/lazycodex-executor-verify/test/cli.test.ts +1 -1
- package/packages/omo-codex/plugin/components/lazycodex-executor-verify/test/codex-hook.test.ts +137 -28
- package/packages/omo-codex/plugin/components/lcx/skills/lcx-doctor/SKILL.md +4 -2
- package/packages/omo-codex/plugin/components/lsp/AGENTS.md +30 -15
- package/packages/omo-codex/plugin/components/lsp/biome.json +2 -2
- package/packages/omo-codex/plugin/components/lsp/dist/.omo-runtime-manifest.json +4 -4
- package/packages/omo-codex/plugin/components/lsp/dist/cli.js +941 -540
- package/packages/omo-codex/plugin/components/lsp/dist/daemon-cli-path.js +1 -1
- package/packages/omo-codex/plugin/components/lsp/hooks/hooks.json +2 -2
- package/packages/omo-codex/plugin/components/lsp/package.json +5 -5
- package/packages/omo-codex/plugin/components/lsp/src/cli.ts +1 -1
- package/packages/omo-codex/plugin/components/lsp/src/codex-hook.ts +1 -1
- package/packages/omo-codex/plugin/components/lsp/src/daemon-cli-path.ts +1 -5
- package/packages/omo-codex/plugin/components/lsp/test/codex-hook-unavailable.test.ts +6 -7
- package/packages/omo-codex/plugin/components/lsp/test/codex-hook.test.ts +1 -2
- package/packages/omo-codex/plugin/components/lsp/test/package-smoke.test.ts +11 -1
- package/packages/omo-codex/plugin/components/rules/AGENTS.md +12 -0
- package/packages/omo-codex/plugin/components/rules/README.md +2 -0
- package/packages/omo-codex/plugin/components/rules/biome.json +2 -2
- package/packages/omo-codex/plugin/components/rules/bundled-rules/hephaestus/gpt-6.md +123 -0
- package/packages/omo-codex/plugin/components/rules/dist/cli.js +91 -68
- package/packages/omo-codex/plugin/components/rules/hooks/hooks.json +4 -4
- package/packages/omo-codex/plugin/components/rules/package.json +7 -7
- package/packages/omo-codex/plugin/components/rules/src/config.ts +1 -2
- package/packages/omo-codex/plugin/components/rules/src/persistent-cache.ts +1 -2
- package/packages/omo-codex/plugin/components/rules/src/post-compact-budget.ts +15 -5
- package/packages/omo-codex/plugin/components/rules/src/rules-engine-factory.ts +1 -4
- package/packages/omo-codex/plugin/components/rules/src/static-injection.ts +4 -9
- package/packages/omo-codex/plugin/components/rules/test/bundled-rules-priority.test.ts +11 -16
- package/packages/omo-codex/plugin/components/rules/test/bundled-rules.test.ts +17 -25
- package/packages/omo-codex/plugin/components/rules/test/codex-hook-post-compact-budget.test.ts +9 -7
- package/packages/omo-codex/plugin/components/rules/test/codex-hook-post-compact-context.test.ts +0 -6
- package/packages/omo-codex/plugin/components/rules/test/codex-hook-post-compact-dedup.test.ts +6 -4
- package/packages/omo-codex/plugin/components/rules/test/codex-hook-post-compact-directive.test.ts +12 -9
- package/packages/omo-codex/plugin/components/rules/test/codex-hook.test.ts +28 -37
- package/packages/omo-codex/plugin/components/rules/test/dynamic-target-fingerprints.test.ts +1 -2
- package/packages/omo-codex/plugin/components/rules/test/engine.test.ts +7 -4
- package/packages/omo-codex/plugin/components/rules/test/finder.test.ts +2 -3
- package/packages/omo-codex/plugin/components/rules/test/formatter.test.ts +39 -72
- package/packages/omo-codex/plugin/components/rules/test/hephaestus-model-variant.test.ts +38 -3
- package/packages/omo-codex/plugin/components/rules/test/hook-output.test.ts +2 -3
- package/packages/omo-codex/plugin/components/rules/test/matcher.test.ts +2 -3
- package/packages/omo-codex/plugin/components/rules/test/package-smoke.test.ts +1 -1
- package/packages/omo-codex/plugin/components/rules/test/parser.test.ts +1 -2
- package/packages/omo-codex/plugin/components/rules/test/post-compact-budget.test.ts +29 -6
- package/packages/omo-codex/plugin/components/rules/test/rules-engine-consumption.test.ts +3 -6
- package/packages/omo-codex/plugin/components/rules/test/scanner.test.ts +1 -2
- package/packages/omo-codex/plugin/components/rules/test/sources.test.ts +2 -5
- package/packages/omo-codex/plugin/components/rules/test/windows-git-bash-bundled-rule.test.ts +2 -17
- package/packages/omo-codex/plugin/components/teammode/hooks/hooks.json +1 -1
- package/packages/omo-codex/plugin/components/teammode/package.json +5 -5
- package/packages/omo-codex/plugin/components/teammode/test/thread-title-hook.test.ts +4 -10
- package/packages/omo-codex/plugin/components/telemetry/AGENTS.md +8 -0
- package/packages/omo-codex/plugin/components/telemetry/biome.json +2 -2
- package/packages/omo-codex/plugin/components/telemetry/dist/cli.js +2407 -684
- package/packages/omo-codex/plugin/components/telemetry/dist/posthog.js +2411 -689
- package/packages/omo-codex/plugin/components/telemetry/hooks/hooks.json +1 -1
- package/packages/omo-codex/plugin/components/telemetry/package.json +5 -5
- package/packages/omo-codex/plugin/components/telemetry/src/codex-hook.ts +1 -4
- package/packages/omo-codex/plugin/components/telemetry/src/posthog.ts +4 -14
- package/packages/omo-codex/plugin/components/telemetry/src/product-identity.ts +1 -1
- package/packages/omo-codex/plugin/components/telemetry/test/diagnostics.test.ts +2 -5
- package/packages/omo-codex/plugin/components/ultrawork/AGENTS.md +10 -4
- package/packages/omo-codex/plugin/components/ultrawork/README.md +2 -0
- package/packages/omo-codex/plugin/components/ultrawork/agents/explorer.toml +1 -1
- package/packages/omo-codex/plugin/components/ultrawork/agents/lazycodex-clone-fidelity-reviewer.toml +1 -1
- package/packages/omo-codex/plugin/components/ultrawork/agents/lazycodex-code-reviewer.toml +1 -1
- package/packages/omo-codex/plugin/components/ultrawork/agents/lazycodex-gate-reviewer.toml +1 -1
- package/packages/omo-codex/plugin/components/ultrawork/agents/lazycodex-qa-executor.toml +1 -1
- package/packages/omo-codex/plugin/components/ultrawork/agents/lazycodex-worker-high.toml +1 -1
- package/packages/omo-codex/plugin/components/ultrawork/agents/lazycodex-worker-low.toml +1 -1
- package/packages/omo-codex/plugin/components/ultrawork/agents/lazycodex-worker-medium.toml +1 -1
- package/packages/omo-codex/plugin/components/ultrawork/agents/librarian.toml +1 -1
- package/packages/omo-codex/plugin/components/ultrawork/agents/metis.toml +1 -1
- package/packages/omo-codex/plugin/components/ultrawork/agents/momus.toml +1 -1
- package/packages/omo-codex/plugin/components/ultrawork/agents/plan.toml +1 -1
- package/packages/omo-codex/plugin/components/ultrawork/biome.json +2 -2
- package/packages/omo-codex/plugin/components/ultrawork/dist/cli.js +490 -4
- package/packages/omo-codex/plugin/components/ultrawork/hooks/hooks.json +1 -1
- package/packages/omo-codex/plugin/components/ultrawork/package.json +5 -6
- package/packages/omo-codex/plugin/components/ultrawork/scripts/sync-directive.mjs +30 -14
- package/packages/omo-codex/plugin/components/ultrawork/skills/ulw-plan/SKILL.md +6 -7
- package/packages/omo-codex/plugin/components/ultrawork/skills/ulw-plan/references/full-workflow.md +31 -7
- package/packages/omo-codex/plugin/components/ultrawork/skills/ulw-plan/references/intent-clear.md +2 -1
- package/packages/omo-codex/plugin/components/ultrawork/skills/ulw-plan/references/intent-unclear.md +5 -5
- package/packages/omo-codex/plugin/components/ultrawork/src/directive-content.ts +4 -0
- package/packages/omo-codex/plugin/components/ultrawork/src/directive.ts +5 -2
- package/packages/omo-codex/plugin/components/ultrawork/test/codex-hook-trigger-policy.test.ts +9 -1
- package/packages/omo-codex/plugin/components/ultrawork/test/codex-hook.test.ts +0 -136
- package/packages/omo-codex/plugin/components/ultrawork/test/directive-source.test.ts +14 -8
- package/packages/omo-codex/plugin/components/ultrawork/test/package-smoke.test.ts +12 -1
- package/packages/omo-codex/plugin/components/ultrawork/test/skill-pointer.test.ts +0 -2
- package/packages/omo-codex/plugin/components/{start-work-continuation → ulw-execute-continuation}/AGENTS.md +4 -4
- package/packages/omo-codex/plugin/components/{start-work-continuation → ulw-execute-continuation}/NOTICE +1 -1
- package/packages/omo-codex/plugin/components/{start-work-continuation → ulw-execute-continuation}/README.md +6 -6
- package/packages/omo-codex/plugin/components/{start-work-continuation → ulw-execute-continuation}/biome.json +2 -2
- package/packages/omo-codex/plugin/components/{start-work-continuation → ulw-execute-continuation}/directive.md +10 -10
- package/packages/omo-codex/plugin/components/{start-work-continuation → ulw-execute-continuation}/dist/cli.js +16 -16
- package/packages/omo-codex/plugin/components/ulw-execute-continuation/hooks/hooks.json +16 -0
- package/packages/omo-codex/plugin/components/{start-work-continuation → ulw-execute-continuation}/package.json +12 -12
- package/packages/omo-codex/plugin/components/{start-work-continuation → ulw-execute-continuation}/src/boulder-reader.ts +1 -1
- package/packages/omo-codex/plugin/components/{start-work-continuation → ulw-execute-continuation}/src/cli.ts +1 -1
- package/packages/omo-codex/plugin/components/{start-work-continuation → ulw-execute-continuation}/src/codex-hook.ts +4 -4
- package/packages/omo-codex/plugin/components/{start-work-continuation → ulw-execute-continuation}/src/directive.ts +1 -1
- package/packages/omo-codex/plugin/components/{start-work-continuation → ulw-execute-continuation}/src/index.ts +1 -1
- package/packages/omo-codex/plugin/components/{start-work-continuation → ulw-execute-continuation}/src/types.ts +1 -1
- package/packages/omo-codex/plugin/components/{start-work-continuation → ulw-execute-continuation}/test/boulder-reader.test.ts +3 -3
- package/packages/omo-codex/plugin/components/{start-work-continuation → ulw-execute-continuation}/test/cli.test.ts +4 -11
- package/packages/omo-codex/plugin/components/{start-work-continuation → ulw-execute-continuation}/test/codex-hook.test.ts +24 -22
- package/packages/omo-codex/plugin/components/ulw-loop/AGENTS.md +19 -0
- package/packages/omo-codex/plugin/components/ulw-loop/CHANGELOG.md +1 -1
- package/packages/omo-codex/plugin/components/ulw-loop/README.md +12 -1
- package/packages/omo-codex/plugin/components/ulw-loop/biome.json +2 -2
- package/packages/omo-codex/plugin/components/ulw-loop/directive.md +26 -13
- package/packages/omo-codex/plugin/components/ulw-loop/dist/checkpoint-codex-validation.d.ts +16 -0
- package/packages/omo-codex/plugin/components/ulw-loop/dist/checkpoint-codex-validation.js +25 -0
- package/packages/omo-codex/plugin/components/ulw-loop/dist/checkpoint-continuation.js +10 -4
- package/packages/omo-codex/plugin/components/ulw-loop/dist/checkpoint-reconciliation.d.ts +2 -5
- package/packages/omo-codex/plugin/components/ulw-loop/dist/checkpoint-reconciliation.js +5 -78
- package/packages/omo-codex/plugin/components/ulw-loop/dist/checkpoint-template.d.ts +12 -0
- package/packages/omo-codex/plugin/components/ulw-loop/dist/checkpoint-template.js +114 -0
- package/packages/omo-codex/plugin/components/ulw-loop/dist/checkpoint.d.ts +7 -1
- package/packages/omo-codex/plugin/components/ulw-loop/dist/checkpoint.js +50 -42
- package/packages/omo-codex/plugin/components/ulw-loop/dist/cli-arg-parser.js +2 -2
- package/packages/omo-codex/plugin/components/ulw-loop/dist/cli-commands.js +21 -8
- package/packages/omo-codex/plugin/components/ulw-loop/dist/cli-output.d.ts +2 -1
- package/packages/omo-codex/plugin/components/ulw-loop/dist/cli-output.js +12 -1
- package/packages/omo-codex/plugin/components/ulw-loop/dist/cli-subcommands.d.ts +1 -1
- package/packages/omo-codex/plugin/components/ulw-loop/dist/cli-subcommands.js +40 -37
- package/packages/omo-codex/plugin/components/ulw-loop/dist/cli.js +1396 -516
- package/packages/omo-codex/plugin/components/ulw-loop/dist/codex-goal-instruction.d.ts +2 -0
- package/packages/omo-codex/plugin/components/ulw-loop/dist/codex-goal-instruction.js +28 -8
- package/packages/omo-codex/plugin/components/ulw-loop/dist/codex-goal-snapshot.d.ts +2 -5
- package/packages/omo-codex/plugin/components/ulw-loop/dist/codex-goal-snapshot.js +24 -20
- package/packages/omo-codex/plugin/components/ulw-loop/dist/constants.d.ts +1 -0
- package/packages/omo-codex/plugin/components/ulw-loop/dist/constants.js +1 -0
- package/packages/omo-codex/plugin/components/ulw-loop/dist/domain-types.d.ts +17 -9
- package/packages/omo-codex/plugin/components/ulw-loop/dist/paths.d.ts +1 -0
- package/packages/omo-codex/plugin/components/ulw-loop/dist/paths.js +13 -4
- package/packages/omo-codex/plugin/components/ulw-loop/dist/plan-io.d.ts +1 -0
- package/packages/omo-codex/plugin/components/ulw-loop/dist/plan-io.js +34 -4
- package/packages/omo-codex/plugin/components/ulw-loop/dist/plan-missing-recovery.d.ts +14 -0
- package/packages/omo-codex/plugin/components/ulw-loop/dist/plan-missing-recovery.js +29 -0
- package/packages/omo-codex/plugin/components/ulw-loop/dist/quality-gate-aggregate.d.ts +7 -0
- package/packages/omo-codex/plugin/components/ulw-loop/dist/quality-gate-aggregate.js +9 -0
- package/packages/omo-codex/plugin/components/ulw-loop/dist/quality-gate-artifacts.d.ts +12 -0
- package/packages/omo-codex/plugin/components/ulw-loop/dist/quality-gate-artifacts.js +104 -0
- package/packages/omo-codex/plugin/components/ulw-loop/dist/quality-gate-fields.d.ts +13 -1
- package/packages/omo-codex/plugin/components/ulw-loop/dist/quality-gate-fields.js +65 -9
- package/packages/omo-codex/plugin/components/ulw-loop/dist/quality-gate-verdicts.js +5 -1
- package/packages/omo-codex/plugin/components/ulw-loop/dist/quality-gate.d.ts +4 -2
- package/packages/omo-codex/plugin/components/ulw-loop/dist/quality-gate.js +72 -117
- package/packages/omo-codex/plugin/components/ulw-loop/dist/review-blockers.d.ts +2 -0
- package/packages/omo-codex/plugin/components/ulw-loop/dist/review-blockers.js +16 -7
- package/packages/omo-codex/plugin/components/ulw-loop/dist/sdk/factory.d.ts +2 -0
- package/packages/omo-codex/plugin/components/ulw-loop/dist/sdk/factory.js +125 -0
- package/packages/omo-codex/plugin/components/ulw-loop/dist/sdk/manifest.d.ts +46 -0
- package/packages/omo-codex/plugin/components/ulw-loop/dist/sdk/manifest.js +28 -0
- package/packages/omo-codex/plugin/components/ulw-loop/dist/sdk/types.d.ts +127 -0
- package/packages/omo-codex/plugin/components/ulw-loop/dist/sdk/types.js +1 -0
- package/packages/omo-codex/plugin/components/ulw-loop/dist/sdk.d.ts +3 -0
- package/packages/omo-codex/plugin/components/ulw-loop/dist/sdk.js +3 -0
- package/packages/omo-codex/plugin/components/ulw-loop/dist/spawn-guard.d.ts +6 -1
- package/packages/omo-codex/plugin/components/ulw-loop/dist/spawn-guard.js +195 -29
- package/packages/omo-codex/plugin/components/ulw-loop/dist/state-lock.d.ts +9 -0
- package/packages/omo-codex/plugin/components/ulw-loop/dist/state-lock.js +227 -0
- package/packages/omo-codex/plugin/components/ulw-loop/dist/status-next-actions.d.ts +6 -0
- package/packages/omo-codex/plugin/components/ulw-loop/dist/status-next-actions.js +33 -0
- package/packages/omo-codex/plugin/components/ulw-loop/dist/stop-resume-hook.js +20 -6
- package/packages/omo-codex/plugin/components/ulw-loop/dist/surface.d.ts +19 -0
- package/packages/omo-codex/plugin/components/ulw-loop/dist/surface.js +75 -0
- package/packages/omo-codex/plugin/components/ulw-loop/hooks/hooks.json +17 -4
- package/packages/omo-codex/plugin/components/ulw-loop/package.json +6 -6
- package/packages/omo-codex/plugin/components/ulw-loop/skills/ulw-loop/SKILL.md +10 -4
- package/packages/omo-codex/plugin/components/ulw-loop/skills/ulw-loop/references/define-goal.md +108 -0
- package/packages/omo-codex/plugin/components/ulw-loop/skills/ulw-loop/references/full-workflow.md +32 -8
- package/packages/omo-codex/plugin/components/ulw-loop/src/checkpoint-codex-validation.ts +40 -0
- package/packages/omo-codex/plugin/components/ulw-loop/src/checkpoint-continuation.ts +8 -6
- package/packages/omo-codex/plugin/components/ulw-loop/src/checkpoint-reconciliation.ts +5 -98
- package/packages/omo-codex/plugin/components/ulw-loop/src/checkpoint-template.ts +134 -0
- package/packages/omo-codex/plugin/components/ulw-loop/src/checkpoint.ts +52 -73
- package/packages/omo-codex/plugin/components/ulw-loop/src/cli-arg-parser.ts +10 -4
- package/packages/omo-codex/plugin/components/ulw-loop/src/cli-commands.ts +24 -8
- package/packages/omo-codex/plugin/components/ulw-loop/src/cli-output.ts +14 -1
- package/packages/omo-codex/plugin/components/ulw-loop/src/cli-subcommands.ts +52 -46
- package/packages/omo-codex/plugin/components/ulw-loop/src/cli.ts +8 -6
- package/packages/omo-codex/plugin/components/ulw-loop/src/codex-goal-instruction.ts +35 -7
- package/packages/omo-codex/plugin/components/ulw-loop/src/codex-goal-snapshot.ts +34 -28
- package/packages/omo-codex/plugin/components/ulw-loop/src/codex-hook.ts +3 -1
- package/packages/omo-codex/plugin/components/ulw-loop/src/constants.ts +1 -0
- package/packages/omo-codex/plugin/components/ulw-loop/src/domain-types.ts +19 -9
- package/packages/omo-codex/plugin/components/ulw-loop/src/paths.ts +25 -4
- package/packages/omo-codex/plugin/components/ulw-loop/src/plan-io.ts +39 -4
- package/packages/omo-codex/plugin/components/ulw-loop/src/plan-missing-recovery.ts +38 -0
- package/packages/omo-codex/plugin/components/ulw-loop/src/quality-gate-aggregate.ts +11 -0
- package/packages/omo-codex/plugin/components/ulw-loop/src/quality-gate-artifacts.ts +123 -0
- package/packages/omo-codex/plugin/components/ulw-loop/src/quality-gate-fields.ts +71 -15
- package/packages/omo-codex/plugin/components/ulw-loop/src/quality-gate-verdicts.ts +6 -1
- package/packages/omo-codex/plugin/components/ulw-loop/src/quality-gate.ts +92 -136
- package/packages/omo-codex/plugin/components/ulw-loop/src/review-blockers.ts +29 -8
- package/packages/omo-codex/plugin/components/ulw-loop/src/sdk/factory.ts +159 -0
- package/packages/omo-codex/plugin/components/ulw-loop/src/sdk/manifest.ts +42 -0
- package/packages/omo-codex/plugin/components/ulw-loop/src/sdk/types.ts +140 -0
- package/packages/omo-codex/plugin/components/ulw-loop/src/sdk.ts +3 -0
- package/packages/omo-codex/plugin/components/ulw-loop/src/spawn-guard.ts +205 -28
- package/packages/omo-codex/plugin/components/ulw-loop/src/state-lock.ts +239 -0
- package/packages/omo-codex/plugin/components/ulw-loop/src/status-next-actions.ts +36 -0
- package/packages/omo-codex/plugin/components/ulw-loop/src/stop-resume-hook.ts +19 -6
- package/packages/omo-codex/plugin/components/ulw-loop/src/surface.ts +107 -0
- package/packages/omo-codex/plugin/components/ulw-loop/test/checkpoint-continuation.test.ts +0 -1
- package/packages/omo-codex/plugin/components/ulw-loop/test/checkpoint-final.test.ts +131 -82
- package/packages/omo-codex/plugin/components/ulw-loop/test/checkpoint-template.test.ts +147 -0
- package/packages/omo-codex/plugin/components/ulw-loop/test/checkpoint.test.ts +16 -22
- package/packages/omo-codex/plugin/components/ulw-loop/test/cli-checkpoint-continuation.test.ts +4 -2
- package/packages/omo-codex/plugin/components/ulw-loop/test/cli-checkpoint.test.ts +31 -2
- package/packages/omo-codex/plugin/components/ulw-loop/test/cli-commands.test.ts +2 -0
- package/packages/omo-codex/plugin/components/ulw-loop/test/cli-complete-goals.test.ts +3 -1
- package/packages/omo-codex/plugin/components/ulw-loop/test/cli-create-goals.test.ts +35 -8
- package/packages/omo-codex/plugin/components/ulw-loop/test/cli-entrypoint.test.ts +38 -4
- package/packages/omo-codex/plugin/components/ulw-loop/test/cli-json-errors.test.ts +27 -0
- package/packages/omo-codex/plugin/components/ulw-loop/test/cli-scope-required.test.ts +144 -0
- package/packages/omo-codex/plugin/components/ulw-loop/test/cli-status-next-actions.test.ts +185 -0
- package/packages/omo-codex/plugin/components/ulw-loop/test/cli-steering-batch.test.ts +8 -3
- package/packages/omo-codex/plugin/components/ulw-loop/test/cli-validation-batch.test.ts +6 -0
- package/packages/omo-codex/plugin/components/ulw-loop/test/codex-goal-instruction.test.ts +37 -2
- package/packages/omo-codex/plugin/components/ulw-loop/test/codex-goal-snapshot.test.ts +52 -11
- package/packages/omo-codex/plugin/components/ulw-loop/test/codex-hook.test.ts +0 -3
- package/packages/omo-codex/plugin/components/ulw-loop/test/fixtures/cli-session.ts +4 -0
- package/packages/omo-codex/plugin/components/ulw-loop/test/fixtures/quality-gate-builder.ts +9 -4
- package/packages/omo-codex/plugin/components/ulw-loop/test/guided-recovery.test.ts +67 -0
- package/packages/omo-codex/plugin/components/ulw-loop/test/package-smoke.test.ts +5 -37
- package/packages/omo-codex/plugin/components/ulw-loop/test/paths.test.ts +9 -0
- package/packages/omo-codex/plugin/components/ulw-loop/test/plan-io-cross-process.test.ts +106 -0
- package/packages/omo-codex/plugin/components/ulw-loop/test/plan-io.test.ts +36 -2
- package/packages/omo-codex/plugin/components/ulw-loop/test/quality-gate-aggregate-basics.test.ts +258 -0
- package/packages/omo-codex/plugin/components/ulw-loop/test/quality-gate-cap-and-dedupe.test.ts +22 -0
- package/packages/omo-codex/plugin/components/ulw-loop/test/quality-gate-fields-messages.test.ts +98 -0
- package/packages/omo-codex/plugin/components/ulw-loop/test/quality-gate-lazycodex-surface.test.ts +93 -0
- package/packages/omo-codex/plugin/components/ulw-loop/test/quality-gate-poisoning-cascades.test.ts +97 -0
- package/packages/omo-codex/plugin/components/ulw-loop/test/quality-gate-roles.test.ts +51 -2
- package/packages/omo-codex/plugin/components/ulw-loop/test/quality-gate-senpi-surface.test.ts +131 -0
- package/packages/omo-codex/plugin/components/ulw-loop/test/quality-gate-single-report.test.ts +241 -0
- package/packages/omo-codex/plugin/components/ulw-loop/test/quality-gate.test.ts +58 -3
- package/packages/omo-codex/plugin/components/ulw-loop/test/review-blockers.test.ts +9 -7
- package/packages/omo-codex/plugin/components/ulw-loop/test/sdk-contract.test.ts +137 -0
- package/packages/omo-codex/plugin/components/ulw-loop/test/sdk-session-context.test.ts +148 -0
- package/packages/omo-codex/plugin/components/ulw-loop/test/spawn-guard.test.ts +444 -7
- package/packages/omo-codex/plugin/components/ulw-loop/test/state-lock.test.ts +218 -0
- package/packages/omo-codex/plugin/components/ulw-loop/test/steering.test.ts +8 -5
- package/packages/omo-codex/plugin/components/ulw-loop/test/stop-resume-hook.test.ts +1 -1
- package/packages/omo-codex/plugin/components/ulw-loop/test/surface.test.ts +74 -0
- package/packages/omo-codex/plugin/components/ulw-loop/test/ultrawork-directive.test.ts +13 -8
- package/packages/omo-codex/plugin/components/ulw-loop/vitest.config.ts +1 -0
- package/packages/omo-codex/plugin/hooks/post-compact-resetting-git-bash-mcp-reminder.json +1 -1
- package/packages/omo-codex/plugin/hooks/post-compact-resetting-lsp-diagnostics-cache.json +1 -1
- package/packages/omo-codex/plugin/hooks/post-compact-resetting-project-rule-cache.json +1 -1
- package/packages/omo-codex/plugin/hooks/post-tool-use-checking-comments.json +1 -1
- package/packages/omo-codex/plugin/hooks/post-tool-use-checking-lsp-diagnostics.json +1 -1
- package/packages/omo-codex/plugin/hooks/post-tool-use-checking-thread-title-hygiene.json +1 -1
- package/packages/omo-codex/plugin/hooks/post-tool-use-matching-project-rules.json +1 -1
- package/packages/omo-codex/plugin/hooks/post-tool-use-recording-spawn-admission.json +18 -0
- package/packages/omo-codex/plugin/hooks/pre-tool-use-enforcing-unlimited-goal-budget.json +1 -1
- package/packages/omo-codex/plugin/hooks/pre-tool-use-guarding-ulw-loop-spawns.json +1 -1
- package/packages/omo-codex/plugin/hooks/pre-tool-use-recommending-git-bash-mcp.json +1 -1
- package/packages/omo-codex/plugin/hooks/session-start-checking-auto-update.json +1 -1
- package/packages/omo-codex/plugin/hooks/session-start-checking-bootstrap-provisioning.json +1 -1
- package/packages/omo-codex/plugin/hooks/session-start-loading-project-rules.json +1 -1
- package/packages/omo-codex/plugin/hooks/session-start-recording-session-telemetry.json +1 -1
- package/packages/omo-codex/plugin/hooks/stop-checking-ulw-execute-continuation.json +17 -0
- package/packages/omo-codex/plugin/hooks/stop-checking-ulw-loop-resume.json +1 -1
- package/packages/omo-codex/plugin/hooks/subagent-stop-verifying-lazycodex-executor-evidence.json +1 -1
- package/packages/omo-codex/plugin/hooks/user-prompt-submit-checking-ultrawork-trigger.json +1 -1
- package/packages/omo-codex/plugin/hooks/user-prompt-submit-checking-ulw-loop-steering.json +1 -1
- package/packages/omo-codex/plugin/hooks/user-prompt-submit-loading-project-rules.json +1 -1
- package/packages/omo-codex/plugin/model-catalog.json +16 -7
- package/packages/omo-codex/plugin/package-lock.json +676 -524
- package/packages/omo-codex/plugin/package.json +2 -3
- package/packages/omo-codex/plugin/scripts/AGENTS.md +39 -0
- package/packages/omo-codex/plugin/scripts/auto-update-plan.mjs +1 -2
- package/packages/omo-codex/plugin/scripts/auto-update.mjs +0 -9
- package/packages/omo-codex/plugin/scripts/canonical-ultrawork-directive.mjs +17 -0
- package/packages/omo-codex/plugin/scripts/hook-status-message.mjs +0 -1
- package/packages/omo-codex/plugin/scripts/migrate-codex-config/catalog.mjs +16 -7
- package/packages/omo-codex/plugin/scripts/migrate-codex-config/multi-agent-v2-guard.mjs +8 -4
- package/packages/omo-codex/plugin/scripts/migrate-codex-config/subagent-limit-guard.mjs +19 -90
- package/packages/omo-codex/plugin/scripts/migrate-codex-config/toml-section-editor.mjs +1 -1
- package/packages/omo-codex/plugin/scripts/sync-skills.mjs +94 -55
- package/packages/omo-codex/plugin/shared/package.json +3 -4
- package/packages/omo-codex/plugin/shared/src/config-loader.ts +2 -102
- package/packages/omo-codex/plugin/shared/src/config-migration.ts +0 -1
- package/packages/omo-codex/plugin/shared/test/config-loader.test.ts +41 -130
- package/packages/omo-codex/plugin/skills/ast-grep/AGENTS.md +51 -0
- package/packages/omo-codex/plugin/skills/ast-grep/SKILL.md +1 -1
- package/packages/omo-codex/plugin/skills/coding-agent-sessions/AGENTS.md +62 -0
- package/packages/omo-codex/plugin/skills/coding-agent-sessions/SKILL.md +1 -1
- package/packages/omo-codex/plugin/skills/data-scientist/SKILL.md +99 -239
- package/packages/omo-codex/plugin/skills/data-scientist/references/execution-surfaces.md +91 -0
- package/packages/omo-codex/plugin/skills/data-scientist/references/placement.md +74 -0
- package/packages/omo-codex/plugin/skills/data-scientist/references/polars-lane.md +95 -0
- package/packages/omo-codex/plugin/skills/data-scientist/references/uv-setup.md +1 -1
- package/packages/omo-codex/plugin/skills/data-scientist/references/visualization.md +64 -0
- package/packages/omo-codex/plugin/skills/data-scientist/scripts/ensure-js-deps.sh +28 -0
- package/packages/omo-codex/plugin/skills/data-scientist/scripts/ensure-py-deps.sh +37 -0
- package/packages/omo-codex/plugin/skills/debugging/SKILL.md +3 -1
- package/packages/omo-codex/plugin/skills/debugging/references/methodology/00-setup.md +12 -0
- package/packages/omo-codex/plugin/skills/debugging/references/methodology/02-investigate.md +21 -0
- package/packages/omo-codex/plugin/skills/debugging/references/runtimes/go.md +15 -1
- package/packages/omo-codex/plugin/skills/debugging/references/runtimes/native-binary.md +38 -0
- package/packages/omo-codex/plugin/skills/debugging/references/runtimes/node.md +25 -0
- package/packages/omo-codex/plugin/skills/debugging/references/runtimes/python.md +13 -0
- package/packages/omo-codex/plugin/skills/debugging/references/runtimes/rust.md +41 -0
- package/packages/omo-codex/plugin/skills/debugging/references/scripts/dap.mjs +267 -0
- package/packages/omo-codex/plugin/skills/debugging/references/scripts/fixture-adapter.mjs +59 -0
- package/packages/omo-codex/plugin/skills/debugging/references/tools/dap.md +103 -0
- package/packages/omo-codex/plugin/skills/debugging/references/tools/frida.md +193 -0
- package/packages/omo-codex/plugin/skills/frontend/ATTRIBUTION.md +10 -0
- package/packages/omo-codex/plugin/skills/frontend/SKILL.md +15 -8
- package/packages/omo-codex/plugin/skills/frontend/references/design/README.md +10 -2
- package/packages/omo-codex/plugin/skills/frontend/references/design/_INDEX.md +2 -0
- package/packages/omo-codex/plugin/skills/frontend/references/design/ambience-skill.md +145 -0
- package/packages/omo-codex/plugin/skills/frontend/references/design/interaction-skill.md +2 -0
- package/packages/omo-codex/plugin/skills/frontend/references/design/print-paged-media.md +76 -0
- package/packages/omo-codex/plugin/skills/frontend/references/design/stylegallery.md +80 -0
- package/packages/omo-codex/plugin/skills/frontend/references/designpowers/README.md +1 -1
- package/packages/omo-codex/plugin/skills/frontend/references/designpowers/lane-a-direction.md +1 -1
- package/packages/omo-codex/plugin/skills/frontend/references/designpowers/lane-b-execution.md +11 -11
- package/packages/omo-codex/plugin/skills/frontend/references/designpowers/lane-d-memory.md +3 -3
- package/packages/omo-codex/plugin/skills/frontend/references/designpowers/orchestration.md +1 -1
- package/packages/omo-codex/plugin/skills/frontend/references/designpowers/routing.md +5 -5
- package/packages/omo-codex/plugin/skills/git-master/SKILL.md +1 -1
- package/packages/omo-codex/plugin/skills/init-deep/SKILL.md +18 -16
- package/packages/omo-codex/plugin/skills/lcx-doctor/SKILL.md +4 -2
- package/packages/omo-codex/plugin/skills/lsp-setup/SKILL.md +1 -1
- package/packages/omo-codex/plugin/skills/programming/SKILL.md +1 -1
- package/packages/omo-codex/plugin/skills/refactor/SKILL.md +8 -6
- package/packages/omo-codex/plugin/skills/remove-ai-slops/SKILL.md +5 -3
- package/packages/omo-codex/plugin/skills/review-work/SKILL.md +114 -422
- package/packages/omo-codex/plugin/skills/ultimate-browsing/ATTRIBUTION.md +38 -11
- package/packages/omo-codex/plugin/skills/ultimate-browsing/SKILL.md +26 -9
- package/packages/omo-codex/plugin/skills/ultimate-browsing/engine/AGENTS.md +110 -0
- package/packages/omo-codex/plugin/skills/ultimate-browsing/engine/templates/package.json +1 -1
- package/packages/omo-codex/plugin/skills/ultimate-browsing/references/chrome-stealth.md +23 -18
- package/packages/omo-codex/plugin/skills/ultimate-browsing/references/insane-search/README.md +9 -2
- package/packages/omo-codex/plugin/skills/ultrawork/SKILL.md +26 -13
- package/packages/omo-codex/plugin/skills/{start-work → ulw-execute}/SKILL.md +29 -31
- package/packages/omo-codex/plugin/skills/ulw-execute/agents/openai.yaml +2 -0
- package/packages/omo-codex/plugin/skills/ulw-loop/SKILL.md +34 -4
- package/packages/omo-codex/plugin/skills/ulw-loop/references/define-goal.md +108 -0
- package/packages/omo-codex/plugin/skills/ulw-loop/references/full-workflow.md +32 -8
- package/packages/omo-codex/plugin/skills/ulw-plan/SKILL.md +6 -7
- package/packages/omo-codex/plugin/skills/ulw-plan/references/full-workflow.md +31 -7
- package/packages/omo-codex/plugin/skills/ulw-plan/references/intent-clear.md +2 -1
- package/packages/omo-codex/plugin/skills/ulw-plan/references/intent-unclear.md +5 -5
- package/packages/omo-codex/plugin/skills/ulw-research/SKILL.md +12 -5
- package/packages/omo-codex/plugin/skills/visual-qa/AGENTS.md +58 -0
- package/packages/omo-codex/plugin/skills/visual-qa/SKILL.md +8 -5
- package/packages/omo-codex/plugin/test/AGENTS.md +47 -0
- package/packages/omo-codex/plugin/test/aggregate-agents.test.mjs +19 -173
- package/packages/omo-codex/plugin/test/aggregate-hooks.test.mjs +16 -51
- package/packages/omo-codex/plugin/test/aggregate-manifest.test.mjs +2 -3
- package/packages/omo-codex/plugin/test/aggregate-mcp.test.mjs +2 -7
- package/packages/omo-codex/plugin/test/aggregate-model-catalog.test.mjs +14 -4
- package/packages/omo-codex/plugin/test/aggregate-plugin-fixture.mjs +175 -13
- package/packages/omo-codex/plugin/test/aggregate.test.mjs +78 -2
- package/packages/omo-codex/plugin/test/auto-update-release-notes.test.mjs +19 -33
- package/packages/omo-codex/plugin/test/auto-update.test.mjs +4 -29
- package/packages/omo-codex/plugin/test/bootstrap-setup.test.mjs +0 -31
- package/packages/omo-codex/plugin/test/canonical-ultrawork-directive.test.mjs +53 -0
- package/packages/omo-codex/plugin/test/component-bin-names.test.mjs +2 -2
- package/packages/omo-codex/plugin/test/component-bundled-cli.test.mjs +1 -51
- package/packages/omo-codex/plugin/test/component-hook-contract-cases.mjs +88 -2
- package/packages/omo-codex/plugin/test/hook-status-message.test.mjs +5 -6
- package/packages/omo-codex/plugin/test/lcx-contribute-bug-fix-template.test.mjs +21 -27
- package/packages/omo-codex/plugin/test/mcp-research-servers.test.mjs +1 -3
- package/packages/omo-codex/plugin/test/migrate-codex-config.test.mjs +35 -35
- package/packages/omo-codex/plugin/test/multi-agent-v2-regression.test.mjs +1 -1
- package/packages/omo-codex/plugin/test/scaffold-plan.test.mjs +0 -36
- package/packages/omo-codex/plugin/test/subagent-limit-migration.test.mjs +107 -15
- package/packages/omo-codex/plugin/test/sync-skills-codex-compatibility.test.mjs +168 -0
- package/packages/omo-codex/plugin/test/sync-skills-test-support.mjs +54 -24
- package/packages/omo-codex/plugin/test/sync-skills.test.mjs +18 -119
- package/packages/omo-codex/plugin/test/teammode-archive-ambiguity.test.mjs +0 -40
- package/packages/omo-codex/plugin/test/teammode-communication.test.mjs +6 -62
- package/packages/omo-codex/plugin/test/teammode-thread-links.test.mjs +3 -36
- package/packages/omo-codex/plugin/test/teammode-transport.test.mjs +0 -44
- package/packages/omo-codex/plugin/test/teammode-worktree.test.mjs +2 -6
- package/packages/omo-codex/plugin/test/ultrawork-skill-pointer.test.mjs +5 -5
- package/packages/omo-codex/plugin/test/ulw-plan-review-state-contract.test.mjs +0 -3
- package/packages/omo-codex/scripts/AGENTS.md +36 -0
- package/packages/omo-codex/scripts/check-model-catalog-parity.mjs +42 -0
- package/packages/omo-codex/scripts/install-cache-copy.test.mjs +27 -1
- package/packages/omo-codex/scripts/install-config-autonomous-features.test.mjs +1 -1
- package/packages/omo-codex/scripts/install-config-autonomous.test.mjs +2 -1
- package/packages/omo-codex/scripts/install-config-git-bash.test.mjs +0 -23
- package/packages/omo-codex/scripts/install-config-reasoning.test.mjs +5 -5
- package/packages/omo-codex/scripts/install-config.test.mjs +15 -17
- package/packages/omo-codex/scripts/install-dist/install-local.mjs +2987 -1370
- package/packages/omo-codex/scripts/install-generated-bundle.test.mjs +3 -4
- package/packages/omo-codex/scripts/install-git-bash-mcp-env.test.mjs +1 -25
- package/packages/omo-codex/scripts/install-lazycodex-version-stamp.test.mjs +7 -2
- package/packages/omo-codex/scripts/install-mcp-runtime.test.mjs +0 -36
- package/packages/omo-codex/scripts/install-packaged-local.test.mjs +1 -6
- package/packages/{omo-codex/plugin/components/ultrawork/skills/ultrawork/SKILL.md → prompts-core/prompts/ultrawork/codex.md} +26 -20
- package/packages/shared-skills/package.json +7 -1
- package/packages/shared-skills/skill-source-filter.d.ts +16 -0
- package/packages/shared-skills/skill-source-filter.mjs +44 -0
- package/packages/shared-skills/skills/ast-grep/AGENTS.md +51 -0
- package/packages/shared-skills/skills/ast-grep/SKILL.md +1 -1
- package/packages/shared-skills/skills/coding-agent-sessions/AGENTS.md +62 -0
- package/packages/shared-skills/skills/coding-agent-sessions/SKILL.md +1 -1
- package/packages/shared-skills/skills/data-scientist/SKILL.md +99 -239
- package/packages/shared-skills/skills/data-scientist/references/execution-surfaces.md +91 -0
- package/packages/shared-skills/skills/data-scientist/references/placement.md +74 -0
- package/packages/shared-skills/skills/data-scientist/references/polars-lane.md +95 -0
- package/packages/shared-skills/skills/data-scientist/references/uv-setup.md +1 -1
- package/packages/shared-skills/skills/data-scientist/references/visualization.md +64 -0
- package/packages/shared-skills/skills/data-scientist/scripts/ensure-js-deps.sh +28 -0
- package/packages/shared-skills/skills/data-scientist/scripts/ensure-py-deps.sh +37 -0
- package/packages/shared-skills/skills/debugging/SKILL.md +3 -1
- package/packages/shared-skills/skills/debugging/references/methodology/00-setup.md +12 -0
- package/packages/shared-skills/skills/debugging/references/methodology/02-investigate.md +21 -0
- package/packages/shared-skills/skills/debugging/references/runtimes/go.md +15 -1
- package/packages/shared-skills/skills/debugging/references/runtimes/native-binary.md +38 -0
- package/packages/shared-skills/skills/debugging/references/runtimes/node.md +25 -0
- package/packages/shared-skills/skills/debugging/references/runtimes/python.md +13 -0
- package/packages/shared-skills/skills/debugging/references/runtimes/rust.md +41 -0
- package/packages/shared-skills/skills/debugging/references/scripts/dap.mjs +267 -0
- package/packages/shared-skills/skills/debugging/references/scripts/dap.test.ts +86 -0
- package/packages/shared-skills/skills/debugging/references/scripts/fixture-adapter.mjs +59 -0
- package/packages/shared-skills/skills/debugging/references/tools/dap.md +103 -0
- package/packages/shared-skills/skills/debugging/references/tools/frida.md +193 -0
- package/packages/shared-skills/skills/frontend/ATTRIBUTION.md +10 -0
- package/packages/shared-skills/skills/frontend/SKILL.md +15 -8
- package/packages/shared-skills/skills/frontend/references/design/README.md +10 -2
- package/packages/shared-skills/skills/frontend/references/design/_INDEX.md +2 -0
- package/packages/shared-skills/skills/frontend/references/design/ambience-skill.md +145 -0
- package/packages/shared-skills/skills/frontend/references/design/interaction-skill.md +2 -0
- package/packages/shared-skills/skills/frontend/references/design/print-paged-media.md +76 -0
- package/packages/shared-skills/skills/frontend/references/design/stylegallery.md +80 -0
- package/packages/shared-skills/skills/frontend/references/designpowers/README.md +1 -1
- package/packages/shared-skills/skills/frontend/references/designpowers/lane-a-direction.md +1 -1
- package/packages/shared-skills/skills/frontend/references/designpowers/lane-b-execution.md +11 -11
- package/packages/shared-skills/skills/frontend/references/designpowers/lane-d-memory.md +3 -3
- package/packages/shared-skills/skills/frontend/references/designpowers/orchestration.md +1 -1
- package/packages/shared-skills/skills/frontend/references/designpowers/routing.md +5 -5
- package/packages/shared-skills/skills/git-master/SKILL.md +1 -1
- package/packages/shared-skills/skills/init-deep/SKILL.md +14 -14
- package/packages/shared-skills/skills/lsp-setup/SKILL.md +1 -1
- package/packages/shared-skills/skills/programming/SKILL.md +1 -1
- package/packages/shared-skills/skills/refactor/SKILL.md +4 -4
- package/packages/shared-skills/skills/remove-ai-slops/SKILL.md +1 -1
- package/packages/shared-skills/skills/review-work/SKILL.md +101 -419
- package/packages/shared-skills/skills/ultimate-browsing/ATTRIBUTION.md +38 -11
- package/packages/shared-skills/skills/ultimate-browsing/SKILL.md +26 -9
- package/packages/shared-skills/skills/ultimate-browsing/engine/AGENTS.md +110 -0
- package/packages/shared-skills/skills/ultimate-browsing/engine/templates/package.json +1 -1
- package/packages/shared-skills/skills/ultimate-browsing/references/chrome-stealth.md +23 -18
- package/packages/shared-skills/skills/ultimate-browsing/references/insane-search/README.md +9 -2
- package/packages/shared-skills/skills/{start-work → ulw-execute}/SKILL.md +20 -19
- package/packages/shared-skills/skills/ulw-plan/SKILL.md +7 -8
- package/packages/shared-skills/skills/ulw-plan/references/full-workflow.md +31 -7
- package/packages/shared-skills/skills/ulw-plan/references/intent-clear.md +2 -1
- package/packages/shared-skills/skills/ulw-plan/references/intent-unclear.md +5 -5
- package/packages/shared-skills/skills/ulw-plan/scripts/scaffold-plan.mjs +1 -1
- package/packages/shared-skills/skills/ulw-research/SKILL.md +8 -3
- package/packages/shared-skills/skills/visual-qa/AGENTS.md +58 -0
- package/packages/shared-skills/skills/visual-qa/SKILL.md +4 -3
- package/postinstall.mjs +2 -0
- package/script/qa/web-terminal-visual-qa.mjs +2 -0
- package/script/qa/xterm-live-terminal.mjs +18 -2
- package/dist/config/schema/codegraph.d.ts +0 -12
- package/dist/config/schema/start-work.d.ts +0 -5
- package/dist/features/builtin-commands/templates/start-work.d.ts +0 -1
- package/dist/features/builtin-skills/index.d.ts +0 -1
- package/dist/features/builtin-skills/skill-file-loader.d.ts +0 -1
- package/dist/features/builtin-skills/skills/agent-browser-skill.d.ts +0 -1
- package/dist/features/builtin-skills/skills/agent-browser-template.d.ts +0 -1
- package/dist/features/builtin-skills/skills/debugging.d.ts +0 -1
- package/dist/features/builtin-skills/skills/dev-browser.d.ts +0 -1
- package/dist/features/builtin-skills/skills/frontend.d.ts +0 -1
- package/dist/features/builtin-skills/skills/git-master-sections/commit-atomic-planning.d.ts +0 -1
- package/dist/features/builtin-skills/skills/git-master-sections/commit-context-analysis.d.ts +0 -1
- package/dist/features/builtin-skills/skills/git-master-sections/commit-execution-verification.d.ts +0 -1
- package/dist/features/builtin-skills/skills/git-master-sections/commit-workflow.d.ts +0 -1
- package/dist/features/builtin-skills/skills/git-master-sections/history-search-workflow.d.ts +0 -1
- package/dist/features/builtin-skills/skills/git-master-sections/overview.d.ts +0 -1
- package/dist/features/builtin-skills/skills/git-master-sections/quick-reference.d.ts +0 -1
- package/dist/features/builtin-skills/skills/git-master-sections/rebase-workflow.d.ts +0 -1
- package/dist/features/builtin-skills/skills/git-master-skill-metadata.d.ts +0 -1
- package/dist/features/builtin-skills/skills/git-master.d.ts +0 -1
- package/dist/features/builtin-skills/skills/index.d.ts +0 -1
- package/dist/features/builtin-skills/skills/init-deep.d.ts +0 -1
- package/dist/features/builtin-skills/skills/playwright-cli.d.ts +0 -1
- package/dist/features/builtin-skills/skills/playwright-mcp-skill.d.ts +0 -1
- package/dist/features/builtin-skills/skills/playwright.d.ts +0 -1
- package/dist/features/builtin-skills/skills/remove-ai-slops.d.ts +0 -1
- package/dist/features/builtin-skills/skills/review-work.d.ts +0 -1
- package/dist/features/builtin-skills/skills/security-research.d.ts +0 -1
- package/dist/features/builtin-skills/skills/security-review.d.ts +0 -1
- package/dist/features/builtin-skills/skills/team-mode.d.ts +0 -1
- package/dist/features/builtin-skills/skills/visual-qa.d.ts +0 -1
- package/dist/features/builtin-skills/skills.d.ts +0 -1
- package/dist/features/builtin-skills/types.d.ts +0 -1
- package/dist/features/claude-code-plugin-loader/agent-loader.d.ts +0 -1
- package/dist/features/claude-code-plugin-loader/command-loader.d.ts +0 -1
- package/dist/features/claude-code-plugin-loader/discovery-core.d.ts +0 -1
- package/dist/features/claude-code-plugin-loader/discovery-paths.d.ts +0 -1
- package/dist/features/claude-code-plugin-loader/discovery.d.ts +0 -1
- package/dist/features/claude-code-plugin-loader/hook-loader.d.ts +0 -1
- package/dist/features/claude-code-plugin-loader/index.d.ts +0 -1
- package/dist/features/claude-code-plugin-loader/install-path-resolver.d.ts +0 -1
- package/dist/features/claude-code-plugin-loader/installed-plugin-database.d.ts +0 -1
- package/dist/features/claude-code-plugin-loader/loaded-plugin.d.ts +0 -1
- package/dist/features/claude-code-plugin-loader/loader.d.ts +0 -1
- package/dist/features/claude-code-plugin-loader/mcp-server-loader.d.ts +0 -1
- package/dist/features/claude-code-plugin-loader/plugin-key.d.ts +0 -1
- package/dist/features/claude-code-plugin-loader/plugin-manifest.d.ts +0 -1
- package/dist/features/claude-code-plugin-loader/plugin-path-resolver.d.ts +0 -1
- package/dist/features/claude-code-plugin-loader/plugin-settings.d.ts +0 -1
- package/dist/features/claude-code-plugin-loader/scope-filter.d.ts +0 -1
- package/dist/features/claude-code-plugin-loader/skill-loader.d.ts +0 -1
- package/dist/features/claude-code-plugin-loader/types.d.ts +0 -1
- package/dist/hooks/codegraph-bootstrap/command-runner.d.ts +0 -17
- package/dist/hooks/codegraph-bootstrap/hook.d.ts +0 -35
- package/dist/hooks/codegraph-bootstrap/index.d.ts +0 -1
- package/dist/hooks/codegraph-bootstrap/project-root.d.ts +0 -1
- package/dist/hooks/codegraph-bootstrap/status.d.ts +0 -11
- package/dist/hooks/ralph-loop/completion-promise-detector-test-input.d.ts +0 -11
- package/dist/hooks/ralph-loop/loop-session-recovery.d.ts +0 -7
- package/dist/hooks/start-work/start-work-hook.d.ts +0 -23
- package/dist/mcp/codegraph.d.ts +0 -16
- package/dist/plugin/chat-message/start-work-message.d.ts +0 -5
- package/dist/shared/prompt-async-gate/message-inspection-error.d.ts +0 -1
- package/dist/shared/prompt-async-gate/pending-tool-turn.d.ts +0 -1
- package/dist/shared/prompt-async-gate/prompt-message-state.d.ts +0 -1
- package/dist/shared/prompt-async-gate/queue.d.ts +0 -1
- package/dist/shared/prompt-async-gate/recent-dispatches.d.ts +0 -1
- package/dist/shared/prompt-async-gate/reservations.d.ts +0 -1
- package/dist/shared/prompt-async-gate/semantic-dedupe.d.ts +0 -1
- package/dist/shared/prompt-async-gate/session-idle-dispatch.d.ts +0 -1
- package/dist/shared/prompt-async-gate/timing.d.ts +0 -1
- package/dist/shared/prompt-async-gate/types.d.ts +0 -1
- package/dist/skills/data-scientist/references/common-scenarios.md +0 -176
- package/dist/skills/data-scientist/references/execution-templates.md +0 -197
- package/dist/skills/data-scientist/references/integration-patterns.md +0 -153
- package/dist/skills/data-scientist/references/performance-benchmarks.md +0 -37
- package/dist/tools/call-omo-agent/background-agent-executor.d.ts +0 -5
- package/dist/tools/call-omo-agent/message-storage-directory.d.ts +0 -1
- package/dist/tools/delegate-task/anthropic-categories.d.ts +0 -2
- package/dist/tools/delegate-task/model-string-parser.d.ts +0 -1
- package/packages/lsp-tools-mcp/dist/lsp/cleanup-errors.d.ts +0 -1
- package/packages/lsp-tools-mcp/dist/lsp/constants.d.ts +0 -1
- package/packages/lsp-tools-mcp/dist/lsp/language-mappings.d.ts +0 -1
- package/packages/lsp-tools-mcp/dist/lsp/process-signal-cleanup.d.ts +0 -1
- package/packages/lsp-tools-mcp/dist/missing-dependency-result.d.ts +0 -1
- package/packages/omo-codex/plugin/components/codegraph/AGENTS.md +0 -58
- package/packages/omo-codex/plugin/components/codegraph/NODE-RUNTIME-LICENSES.md +0 -2951
- package/packages/omo-codex/plugin/components/codegraph/NOTICE +0 -16
- package/packages/omo-codex/plugin/components/codegraph/dist/cli.js +0 -12149
- package/packages/omo-codex/plugin/components/codegraph/dist/serve.js +0 -9747
- package/packages/omo-codex/plugin/components/codegraph/package.json +0 -33
- package/packages/omo-codex/plugin/components/codegraph/src/cache-gc.ts +0 -29
- package/packages/omo-codex/plugin/components/codegraph/src/cli.ts +0 -79
- package/packages/omo-codex/plugin/components/codegraph/src/hook-input.ts +0 -33
- package/packages/omo-codex/plugin/components/codegraph/src/hook-sweep.ts +0 -25
- package/packages/omo-codex/plugin/components/codegraph/src/hook-types.ts +0 -131
- package/packages/omo-codex/plugin/components/codegraph/src/hook.ts +0 -258
- package/packages/omo-codex/plugin/components/codegraph/src/mcp-bridge.ts +0 -309
- package/packages/omo-codex/plugin/components/codegraph/src/mcp-unavailable.ts +0 -80
- package/packages/omo-codex/plugin/components/codegraph/src/post-tool-use-hook.ts +0 -34
- package/packages/omo-codex/plugin/components/codegraph/src/serve-invocation.ts +0 -29
- package/packages/omo-codex/plugin/components/codegraph/src/serve.ts +0 -263
- package/packages/omo-codex/plugin/components/codegraph/src/session-start-command.ts +0 -106
- package/packages/omo-codex/plugin/components/codegraph/src/session-start-cooldown.ts +0 -145
- package/packages/omo-codex/plugin/components/codegraph/src/session-start-hook-runtime.ts +0 -21
- package/packages/omo-codex/plugin/components/codegraph/src/session-start-lock.ts +0 -139
- package/packages/omo-codex/plugin/components/codegraph/src/session-start-outcome.ts +0 -15
- package/packages/omo-codex/plugin/components/codegraph/src/session-start-paths.ts +0 -32
- package/packages/omo-codex/plugin/components/codegraph/src/session-start-project.ts +0 -109
- package/packages/omo-codex/plugin/components/codegraph/src/session-start-worker-result.ts +0 -148
- package/packages/omo-codex/plugin/components/codegraph/src/session-start-worker.ts +0 -175
- package/packages/omo-codex/plugin/components/codegraph/src/sweep-cli.ts +0 -81
- package/packages/omo-codex/plugin/components/codegraph/test/cache-gc.test.ts +0 -34
- package/packages/omo-codex/plugin/components/codegraph/test/hook-exclusion.test.ts +0 -112
- package/packages/omo-codex/plugin/components/codegraph/test/hook-registration.test.ts +0 -26
- package/packages/omo-codex/plugin/components/codegraph/test/hook-session-start-guard.test.ts +0 -160
- package/packages/omo-codex/plugin/components/codegraph/test/hook-store-upgrade.test.ts +0 -50
- package/packages/omo-codex/plugin/components/codegraph/test/hook-sweep.test.ts +0 -29
- package/packages/omo-codex/plugin/components/codegraph/test/hook.test.ts +0 -320
- package/packages/omo-codex/plugin/components/codegraph/test/mcp-bridge-fixtures.ts +0 -172
- package/packages/omo-codex/plugin/components/codegraph/test/package-runtime.test.ts +0 -91
- package/packages/omo-codex/plugin/components/codegraph/test/provisioned-node-guard.test.ts +0 -100
- package/packages/omo-codex/plugin/components/codegraph/test/serve-built-wrapper.test.ts +0 -76
- package/packages/omo-codex/plugin/components/codegraph/test/serve-mcp-bridge-lifecycle.test.ts +0 -133
- package/packages/omo-codex/plugin/components/codegraph/test/serve-mcp-bridge.test.ts +0 -245
- package/packages/omo-codex/plugin/components/codegraph/test/serve-mcp-facade.test.ts +0 -69
- package/packages/omo-codex/plugin/components/codegraph/test/serve-node-support.test.ts +0 -43
- package/packages/omo-codex/plugin/components/codegraph/test/serve-provision.test.ts +0 -147
- package/packages/omo-codex/plugin/components/codegraph/test/serve-unavailable.test.ts +0 -175
- package/packages/omo-codex/plugin/components/codegraph/test/serve.test.ts +0 -385
- package/packages/omo-codex/plugin/components/codegraph/test/session-start-node-support.test.ts +0 -206
- package/packages/omo-codex/plugin/components/codegraph/test/session-start-project.test.ts +0 -58
- package/packages/omo-codex/plugin/components/codegraph/test/session-start-state.test.ts +0 -104
- package/packages/omo-codex/plugin/components/codegraph/test/session-start-trust-boundary.test.ts +0 -65
- package/packages/omo-codex/plugin/components/codegraph/test/session-start-worker-availability.test.ts +0 -106
- package/packages/omo-codex/plugin/components/codegraph/test/session-start-worker-cooldown.test.ts +0 -116
- package/packages/omo-codex/plugin/components/codegraph/test/session-start-worker-flow.test.ts +0 -258
- package/packages/omo-codex/plugin/components/codegraph/test/sweep-cli.test.ts +0 -56
- package/packages/omo-codex/plugin/components/codegraph/tsconfig.build.json +0 -13
- package/packages/omo-codex/plugin/components/codegraph/tsconfig.json +0 -25
- package/packages/omo-codex/plugin/components/start-work-continuation/LICENSE +0 -21
- package/packages/omo-codex/plugin/components/start-work-continuation/hooks/hooks.json +0 -28
- package/packages/omo-codex/plugin/components/ultrawork/directive.md +0 -471
- package/packages/omo-codex/plugin/hooks/post-tool-use-checking-codegraph-init-guidance.json +0 -18
- package/packages/omo-codex/plugin/hooks/session-start-checking-codegraph-bootstrap.json +0 -17
- package/packages/omo-codex/plugin/hooks/stop-checking-start-work-continuation.json +0 -17
- package/packages/omo-codex/plugin/hooks/subagent-stop-checking-start-work-continuation.json +0 -17
- package/packages/omo-codex/plugin/scripts/migrate-omo-sot/editor.mjs +0 -125
- package/packages/omo-codex/plugin/scripts/migrate-omo-sot/jsonc.mjs +0 -43
- package/packages/omo-codex/plugin/scripts/migrate-omo-sot/scaffold.mjs +0 -29
- package/packages/omo-codex/plugin/scripts/migrate-omo-sot.mjs +0 -121
- package/packages/omo-codex/plugin/skills/data-scientist/references/common-scenarios.md +0 -176
- package/packages/omo-codex/plugin/skills/data-scientist/references/execution-templates.md +0 -197
- package/packages/omo-codex/plugin/skills/data-scientist/references/integration-patterns.md +0 -153
- package/packages/omo-codex/plugin/skills/data-scientist/references/performance-benchmarks.md +0 -37
- package/packages/omo-codex/plugin/skills/start-work/agents/openai.yaml +0 -2
- package/packages/omo-codex/plugin/test/aggregate-skills.test.mjs +0 -92
- package/packages/omo-codex/plugin/test/component-codegraph-mcp-smoke.test.mjs +0 -76
- package/packages/omo-codex/plugin/test/migrate-omo-sot.test.mjs +0 -179
- package/packages/omo-codex/plugin/test/sync-skills-orchestration.test.mjs +0 -314
- package/packages/omo-codex/plugin/test/ulw-plan-scope-contract.test.mjs +0 -24
- package/packages/shared-skills/skills/data-scientist/references/common-scenarios.md +0 -176
- package/packages/shared-skills/skills/data-scientist/references/execution-templates.md +0 -197
- package/packages/shared-skills/skills/data-scientist/references/integration-patterns.md +0 -153
- package/packages/shared-skills/skills/data-scientist/references/performance-benchmarks.md +0 -37
- /package/dist/hooks/{start-work → ulw-execute}/context-info-formatters.d.ts +0 -0
- /package/dist/hooks/{start-work → ulw-execute}/explicit-plan-context.d.ts +0 -0
- /package/dist/hooks/{start-work → ulw-execute}/notepad-scaffold.d.ts +0 -0
- /package/dist/hooks/{start-work → ulw-execute}/parse-user-request.d.ts +0 -0
- /package/dist/hooks/{start-work → ulw-execute}/plan-discovery-context.d.ts +0 -0
- /package/dist/hooks/{start-work → ulw-execute}/plan-selection.d.ts +0 -0
- /package/dist/hooks/{start-work → ulw-execute}/session-plan-affinity.d.ts +0 -0
- /package/dist/hooks/{start-work → ulw-execute}/work-initializer.d.ts +0 -0
- /package/dist/hooks/{start-work → ulw-execute}/worktree-block.d.ts +0 -0
- /package/dist/hooks/{start-work → ulw-execute}/worktree-detector.d.ts +0 -0
- /package/packages/omo-codex/plugin/components/{start-work-continuation → ulw-execute-continuation}/.gitattributes +0 -0
- /package/packages/omo-codex/plugin/components/{start-work-continuation → ulw-execute-continuation}/CHANGELOG.md +0 -0
- /package/packages/omo-codex/plugin/components/{codegraph → ulw-execute-continuation}/LICENSE +0 -0
- /package/packages/omo-codex/plugin/components/{start-work-continuation → ulw-execute-continuation}/src/plan-checklist.ts +0 -0
- /package/packages/omo-codex/plugin/components/{start-work-continuation → ulw-execute-continuation}/test/fixtures/boulder-completed.json +0 -0
- /package/packages/omo-codex/plugin/components/{start-work-continuation → ulw-execute-continuation}/test/fixtures/boulder-mixed-platforms.json +0 -0
- /package/packages/omo-codex/plugin/components/{start-work-continuation → ulw-execute-continuation}/test/fixtures/boulder-single-codex-work.json +0 -0
- /package/packages/omo-codex/plugin/components/{start-work-continuation → ulw-execute-continuation}/test/fixtures/plan-all-done.md +0 -0
- /package/packages/omo-codex/plugin/components/{start-work-continuation → ulw-execute-continuation}/test/fixtures/plan-scaffold.md +0 -0
- /package/packages/omo-codex/plugin/components/{start-work-continuation → ulw-execute-continuation}/test/fixtures/plan-with-nested-checkboxes.md +0 -0
- /package/packages/omo-codex/plugin/components/{start-work-continuation → ulw-execute-continuation}/test/fixtures/plan-with-unchecked.md +0 -0
- /package/packages/omo-codex/plugin/components/{start-work-continuation → ulw-execute-continuation}/tsconfig.build.json +0 -0
- /package/packages/omo-codex/plugin/components/{start-work-continuation → ulw-execute-continuation}/tsconfig.json +0 -0
- /package/packages/omo-codex/plugin/components/{start-work-continuation → ulw-execute-continuation}/vitest.config.ts +0 -0
|
@@ -15,6 +15,13 @@ import { pathToFileURL as pathToFileURL3 } from "node:url";
|
|
|
15
15
|
// ../lsp-core/src/lsp/connection.ts
|
|
16
16
|
import { pathToFileURL } from "node:url";
|
|
17
17
|
|
|
18
|
+
// ../lsp-core/src/lsp/timer-provider.ts
|
|
19
|
+
var realTimerProvider = {
|
|
20
|
+
now: () => Date.now(),
|
|
21
|
+
setTimeout: (callback, delayMs) => setTimeout(callback, delayMs),
|
|
22
|
+
clearTimeout: (handle) => clearTimeout(handle)
|
|
23
|
+
};
|
|
24
|
+
|
|
18
25
|
// ../lsp-core/src/lsp/constants.ts
|
|
19
26
|
var DEFAULT_MAX_REFERENCES = 200;
|
|
20
27
|
var DEFAULT_MAX_SYMBOLS = 200;
|
|
@@ -23,28 +30,24 @@ var DEFAULT_MAX_DIRECTORY_FILES = 50;
|
|
|
23
30
|
var REQUEST_TIMEOUT_MS = 15000;
|
|
24
31
|
var INIT_TIMEOUT_MS = 60000;
|
|
25
32
|
var IDLE_TIMEOUT_MS = 5 * 60000;
|
|
33
|
+
var MAX_RESIDENT_CLIENTS = 6;
|
|
26
34
|
var REAPER_INTERVAL_MS = 60000;
|
|
27
35
|
var STOP_HARD_KILL_TIMEOUT_MS = 5000;
|
|
28
36
|
var STOP_SIGKILL_GRACE_MS = 1000;
|
|
37
|
+
var CLIENT_RESPAWN_RETRY_LIMIT = 2;
|
|
38
|
+
var CLIENT_RESPAWN_COOLDOWN_MS = 60000;
|
|
29
39
|
|
|
30
40
|
// ../lsp-core/src/lsp/errors.ts
|
|
31
41
|
class LspConnectionClosedError extends Error {
|
|
32
|
-
serverId;
|
|
33
|
-
root;
|
|
34
|
-
name = "LspConnectionClosedError";
|
|
35
42
|
constructor(serverId, root, message) {
|
|
36
43
|
super(message ?? `LSP connection closed for ${serverId} at ${root}`);
|
|
37
44
|
this.serverId = serverId;
|
|
38
45
|
this.root = root;
|
|
46
|
+
this.name = "LspConnectionClosedError";
|
|
39
47
|
}
|
|
40
48
|
}
|
|
41
49
|
|
|
42
50
|
class LspProcessExitedError extends Error {
|
|
43
|
-
serverId;
|
|
44
|
-
root;
|
|
45
|
-
exitCode;
|
|
46
|
-
stderrTail;
|
|
47
|
-
name = "LspProcessExitedError";
|
|
48
51
|
constructor(serverId, root, exitCode, stderrTail) {
|
|
49
52
|
const stderrSuffix = stderrTail ? `
|
|
50
53
|
stderr tail: ${stderrTail}` : "";
|
|
@@ -53,46 +56,59 @@ stderr tail: ${stderrTail}` : "";
|
|
|
53
56
|
this.root = root;
|
|
54
57
|
this.exitCode = exitCode;
|
|
55
58
|
this.stderrTail = stderrTail;
|
|
59
|
+
this.name = "LspProcessExitedError";
|
|
56
60
|
}
|
|
57
61
|
}
|
|
58
62
|
|
|
59
63
|
class LspRequestTimeoutError extends Error {
|
|
60
|
-
method;
|
|
61
|
-
stderrTail;
|
|
62
|
-
name = "LspRequestTimeoutError";
|
|
63
64
|
constructor(method, stderrTail) {
|
|
64
65
|
const stderrSuffix = stderrTail ? `
|
|
65
66
|
recent stderr: ${stderrTail}` : "";
|
|
66
67
|
super(`LSP request timeout (method: ${method})${stderrSuffix}`);
|
|
67
68
|
this.method = method;
|
|
68
69
|
this.stderrTail = stderrTail;
|
|
70
|
+
this.name = "LspRequestTimeoutError";
|
|
69
71
|
}
|
|
70
72
|
}
|
|
71
73
|
|
|
72
74
|
class LspInvalidPathError extends Error {
|
|
73
|
-
|
|
75
|
+
constructor() {
|
|
76
|
+
super(...arguments);
|
|
77
|
+
this.name = "LspInvalidPathError";
|
|
78
|
+
}
|
|
74
79
|
}
|
|
75
80
|
|
|
76
81
|
class LspServerLookupError extends Error {
|
|
77
|
-
lookup;
|
|
78
|
-
name = "LspServerLookupError";
|
|
79
82
|
constructor(message, lookup) {
|
|
80
83
|
super(message);
|
|
81
84
|
this.lookup = lookup;
|
|
85
|
+
this.name = "LspServerLookupError";
|
|
82
86
|
}
|
|
83
87
|
}
|
|
84
88
|
|
|
85
89
|
class LspServerInitializingError extends Error {
|
|
86
|
-
originalError;
|
|
87
|
-
name = "LspServerInitializingError";
|
|
88
90
|
constructor(originalError) {
|
|
89
91
|
super(`LSP server is still initializing. Please retry in a few seconds. Original error: ${originalError.message}`);
|
|
90
92
|
this.originalError = originalError;
|
|
93
|
+
this.name = "LspServerInitializingError";
|
|
91
94
|
}
|
|
92
95
|
}
|
|
93
96
|
|
|
94
97
|
class LspProcessSpawnError extends Error {
|
|
95
|
-
|
|
98
|
+
constructor() {
|
|
99
|
+
super(...arguments);
|
|
100
|
+
this.name = "LspProcessSpawnError";
|
|
101
|
+
}
|
|
102
|
+
}
|
|
103
|
+
|
|
104
|
+
class LspClientRespawnBudgetExceededError extends Error {
|
|
105
|
+
constructor(serverId, root, retryLimit) {
|
|
106
|
+
super(`LSP server ${serverId} at ${root} failed to stay alive; respawn budget exhausted ` + `(${retryLimit} consecutive dead generations). Retrying after the cooldown may succeed.`);
|
|
107
|
+
this.serverId = serverId;
|
|
108
|
+
this.root = root;
|
|
109
|
+
this.retryLimit = retryLimit;
|
|
110
|
+
this.name = "LspClientRespawnBudgetExceededError";
|
|
111
|
+
}
|
|
96
112
|
}
|
|
97
113
|
function isLspDeadConnectionError(err) {
|
|
98
114
|
return err instanceof LspConnectionClosedError || err instanceof LspProcessExitedError;
|
|
@@ -108,20 +124,31 @@ var METHOD_NOT_FOUND = -32601;
|
|
|
108
124
|
var INTERNAL_ERROR = -32603;
|
|
109
125
|
|
|
110
126
|
class JsonRpcConnection {
|
|
111
|
-
reader;
|
|
112
|
-
writer;
|
|
113
|
-
pendingRequests = new Map;
|
|
114
|
-
notificationHandlers = new Map;
|
|
115
|
-
requestHandlers = new Map;
|
|
116
|
-
closeHandlers = [];
|
|
117
|
-
errorHandlers = [];
|
|
118
|
-
inputBuffer = Buffer.alloc(0);
|
|
119
|
-
nextRequestId = 1;
|
|
120
|
-
listening = false;
|
|
121
|
-
disposed = false;
|
|
122
127
|
constructor(reader, writer) {
|
|
123
128
|
this.reader = reader;
|
|
124
129
|
this.writer = writer;
|
|
130
|
+
this.pendingRequests = new Map;
|
|
131
|
+
this.notificationHandlers = new Map;
|
|
132
|
+
this.requestHandlers = new Map;
|
|
133
|
+
this.closeHandlers = [];
|
|
134
|
+
this.errorHandlers = [];
|
|
135
|
+
this.inputBuffer = Buffer.alloc(0);
|
|
136
|
+
this.nextRequestId = 1;
|
|
137
|
+
this.listening = false;
|
|
138
|
+
this.disposed = false;
|
|
139
|
+
this.handleData = (chunk) => {
|
|
140
|
+
const chunkBuffer = Buffer.isBuffer(chunk) ? chunk : Buffer.from(chunk, "utf8");
|
|
141
|
+
this.inputBuffer = Buffer.concat([this.inputBuffer, chunkBuffer]);
|
|
142
|
+
this.drainInputBuffer();
|
|
143
|
+
};
|
|
144
|
+
this.handleClose = () => {
|
|
145
|
+
for (const handler of this.closeHandlers) {
|
|
146
|
+
handler();
|
|
147
|
+
}
|
|
148
|
+
};
|
|
149
|
+
this.handleStreamError = (error) => {
|
|
150
|
+
this.emitError(error);
|
|
151
|
+
};
|
|
125
152
|
}
|
|
126
153
|
listen() {
|
|
127
154
|
if (this.listening)
|
|
@@ -156,6 +183,7 @@ class JsonRpcConnection {
|
|
|
156
183
|
let cancelAfterWrite = false;
|
|
157
184
|
let settled = false;
|
|
158
185
|
const writeCancel = () => this.writeMessage({ jsonrpc: "2.0", method: "$/cancelRequest", params: { id } });
|
|
186
|
+
let rejectAfterCancelWrite;
|
|
159
187
|
const responsePromise = new Promise((resolve, reject) => {
|
|
160
188
|
const cleanup = () => {
|
|
161
189
|
options.signal?.removeEventListener("abort", onAbort);
|
|
@@ -167,15 +195,19 @@ class JsonRpcConnection {
|
|
|
167
195
|
this.pendingRequests.delete(key);
|
|
168
196
|
cleanup();
|
|
169
197
|
const rejectCancelled = () => reject(abortError(options.signal));
|
|
198
|
+
rejectAfterCancelWrite = async () => {
|
|
199
|
+
try {
|
|
200
|
+
await writeCancel();
|
|
201
|
+
} catch (error) {
|
|
202
|
+
this.emitError(toError(error));
|
|
203
|
+
}
|
|
204
|
+
rejectCancelled();
|
|
205
|
+
};
|
|
170
206
|
if (!requestWritten) {
|
|
171
207
|
cancelAfterWrite = true;
|
|
172
|
-
rejectCancelled();
|
|
173
208
|
return;
|
|
174
209
|
}
|
|
175
|
-
|
|
176
|
-
this.emitError(toError(error));
|
|
177
|
-
rejectCancelled();
|
|
178
|
-
});
|
|
210
|
+
rejectAfterCancelWrite();
|
|
179
211
|
};
|
|
180
212
|
const onAbort = () => settleCancel();
|
|
181
213
|
this.pendingRequests.set(key, {
|
|
@@ -203,7 +235,7 @@ class JsonRpcConnection {
|
|
|
203
235
|
await this.writeMessage(message);
|
|
204
236
|
requestWritten = true;
|
|
205
237
|
if (cancelAfterWrite)
|
|
206
|
-
await
|
|
238
|
+
await rejectAfterCancelWrite?.();
|
|
207
239
|
} catch (error) {
|
|
208
240
|
if (settled)
|
|
209
241
|
return responsePromise;
|
|
@@ -242,19 +274,6 @@ class JsonRpcConnection {
|
|
|
242
274
|
this.notificationHandlers.clear();
|
|
243
275
|
this.requestHandlers.clear();
|
|
244
276
|
}
|
|
245
|
-
handleData = (chunk) => {
|
|
246
|
-
const chunkBuffer = Buffer.isBuffer(chunk) ? chunk : Buffer.from(chunk, "utf8");
|
|
247
|
-
this.inputBuffer = Buffer.concat([this.inputBuffer, chunkBuffer]);
|
|
248
|
-
this.drainInputBuffer();
|
|
249
|
-
};
|
|
250
|
-
handleClose = () => {
|
|
251
|
-
for (const handler of this.closeHandlers) {
|
|
252
|
-
handler();
|
|
253
|
-
}
|
|
254
|
-
};
|
|
255
|
-
handleStreamError = (error) => {
|
|
256
|
-
this.emitError(error);
|
|
257
|
-
};
|
|
258
277
|
drainInputBuffer() {
|
|
259
278
|
while (true) {
|
|
260
279
|
const headerEnd = this.inputBuffer.indexOf(HEADER_SEPARATOR);
|
|
@@ -602,33 +621,29 @@ function isPosition(value) {
|
|
|
602
621
|
|
|
603
622
|
// ../lsp-core/src/lsp/transport.ts
|
|
604
623
|
class LspClientNotStartedError extends Error {
|
|
605
|
-
serverId;
|
|
606
|
-
root;
|
|
607
|
-
name = "LspClientNotStartedError";
|
|
608
624
|
constructor(serverId, root) {
|
|
609
625
|
super("LSP client not started");
|
|
610
626
|
this.serverId = serverId;
|
|
611
627
|
this.root = root;
|
|
628
|
+
this.name = "LspClientNotStartedError";
|
|
612
629
|
}
|
|
613
630
|
}
|
|
614
631
|
|
|
615
632
|
class LspClientTransport {
|
|
616
|
-
root;
|
|
617
|
-
server;
|
|
618
|
-
proc = null;
|
|
619
|
-
connection = null;
|
|
620
|
-
stderrBuffer = [];
|
|
621
|
-
processExited = false;
|
|
622
|
-
diagnosticsStore = new Map;
|
|
623
|
-
requestTimeoutMs;
|
|
624
|
-
initializeTimeoutMs;
|
|
625
|
-
workspaceApplyEditHandler = null;
|
|
626
|
-
diagnosticPullSupported = false;
|
|
627
633
|
constructor(root, server, timeouts = {}) {
|
|
628
634
|
this.root = root;
|
|
629
635
|
this.server = server;
|
|
636
|
+
this.proc = null;
|
|
637
|
+
this.connection = null;
|
|
638
|
+
this.stderrBuffer = [];
|
|
639
|
+
this.processExited = false;
|
|
640
|
+
this.diagnosticsStore = new Map;
|
|
641
|
+
this.workspaceApplyEditHandler = null;
|
|
642
|
+
this.diagnosticPullSupported = false;
|
|
643
|
+
this.documentFormattingSupported = false;
|
|
630
644
|
this.requestTimeoutMs = timeouts.requestTimeoutMs ?? REQUEST_TIMEOUT_MS;
|
|
631
645
|
this.initializeTimeoutMs = timeouts.initializeTimeoutMs ?? INIT_TIMEOUT_MS;
|
|
646
|
+
this.timerProvider = timeouts.timerProvider ?? realTimerProvider;
|
|
632
647
|
}
|
|
633
648
|
pid() {
|
|
634
649
|
return this.proc?.pid;
|
|
@@ -648,6 +663,12 @@ class LspClientTransport {
|
|
|
648
663
|
isDiagnosticPullSupported() {
|
|
649
664
|
return this.diagnosticPullSupported;
|
|
650
665
|
}
|
|
666
|
+
setDocumentFormattingSupported(supported) {
|
|
667
|
+
this.documentFormattingSupported = supported;
|
|
668
|
+
}
|
|
669
|
+
isDocumentFormattingSupported() {
|
|
670
|
+
return this.documentFormattingSupported;
|
|
671
|
+
}
|
|
651
672
|
handlePublishDiagnostics(params) {
|
|
652
673
|
this.diagnosticsStore.set(params.uri, [...params.diagnostics]);
|
|
653
674
|
}
|
|
@@ -723,7 +744,7 @@ class LspClientTransport {
|
|
|
723
744
|
const options = args[1];
|
|
724
745
|
const timeoutMs = options?.timeoutMs ?? this.requestTimeoutMs;
|
|
725
746
|
const timeoutController = new AbortController;
|
|
726
|
-
const timeoutHandle = setTimeout(() => {
|
|
747
|
+
const timeoutHandle = this.timerProvider.setTimeout(() => {
|
|
727
748
|
const stderrTail = this.stderrBuffer.slice(-5).join(`
|
|
728
749
|
`);
|
|
729
750
|
timeoutController.abort(new LspRequestTimeoutError(method, stderrTail || undefined));
|
|
@@ -742,7 +763,7 @@ class LspClientTransport {
|
|
|
742
763
|
}
|
|
743
764
|
throw error;
|
|
744
765
|
} finally {
|
|
745
|
-
clearTimeout(timeoutHandle);
|
|
766
|
+
this.timerProvider.clearTimeout(timeoutHandle);
|
|
746
767
|
combinedSignal.dispose();
|
|
747
768
|
}
|
|
748
769
|
}
|
|
@@ -861,6 +882,14 @@ function supportsDiagnosticPull(capabilities) {
|
|
|
861
882
|
return false;
|
|
862
883
|
return Object.hasOwn(capabilities, "diagnosticProvider");
|
|
863
884
|
}
|
|
885
|
+
function supportsDocumentFormatting(capabilities) {
|
|
886
|
+
if (capabilities === undefined)
|
|
887
|
+
return false;
|
|
888
|
+
const provider = capabilities.documentFormattingProvider;
|
|
889
|
+
if (provider === undefined || provider === null || provider === false)
|
|
890
|
+
return false;
|
|
891
|
+
return provider === true || typeof provider === "object";
|
|
892
|
+
}
|
|
864
893
|
|
|
865
894
|
class LspClientConnection extends LspClientTransport {
|
|
866
895
|
async initialize() {
|
|
@@ -877,6 +906,7 @@ class LspClientConnection extends LspClientTransport {
|
|
|
877
906
|
references: {},
|
|
878
907
|
documentSymbol: { hierarchicalDocumentSymbolSupport: true },
|
|
879
908
|
publishDiagnostics: {},
|
|
909
|
+
formatting: { dynamicRegistration: false },
|
|
880
910
|
rename: {
|
|
881
911
|
prepareSupport: true,
|
|
882
912
|
prepareSupportDefaultBehavior: 1
|
|
@@ -918,6 +948,7 @@ class LspClientConnection extends LspClientTransport {
|
|
|
918
948
|
initializationOptions: this.server.initialization
|
|
919
949
|
}, { timeoutMs: this.initializeTimeoutMs });
|
|
920
950
|
this.setDiagnosticPullSupported(supportsDiagnosticPull(result?.capabilities));
|
|
951
|
+
this.setDocumentFormattingSupported(supportsDocumentFormatting(result?.capabilities));
|
|
921
952
|
await this.sendNotification("initialized", {});
|
|
922
953
|
await this.sendNotification("workspace/didChangeConfiguration", {
|
|
923
954
|
settings: { json: { validate: { enable: true } } }
|
|
@@ -1123,6 +1154,17 @@ function canonicalPath(filePath) {
|
|
|
1123
1154
|
return absolute;
|
|
1124
1155
|
}
|
|
1125
1156
|
}
|
|
1157
|
+
function normalizeDocumentUri(uri) {
|
|
1158
|
+
let decoded = uri;
|
|
1159
|
+
try {
|
|
1160
|
+
decoded = decodeURIComponent(uri);
|
|
1161
|
+
} catch {
|
|
1162
|
+
decoded = uri;
|
|
1163
|
+
}
|
|
1164
|
+
if (process.platform !== "win32")
|
|
1165
|
+
return decoded;
|
|
1166
|
+
return decoded.replace(/^(file:\/\/\/)([a-z]):/, (_match, prefix, drive) => `${prefix}${drive.toUpperCase()}:`);
|
|
1167
|
+
}
|
|
1126
1168
|
function isSameOrDescendant(candidate, parent) {
|
|
1127
1169
|
const suffix = relative(parent, candidate);
|
|
1128
1170
|
return suffix === "" || !suffix.startsWith("..") && suffix !== "..";
|
|
@@ -1133,17 +1175,18 @@ function movedPath(candidate, oldPath, newPath) {
|
|
|
1133
1175
|
}
|
|
1134
1176
|
|
|
1135
1177
|
class WorkspaceDocumentState {
|
|
1136
|
-
sendNotification;
|
|
1137
|
-
clearDiagnostics;
|
|
1138
|
-
openDocuments = new Map;
|
|
1139
|
-
openByUri = new Map;
|
|
1140
|
-
openPromises = new Map;
|
|
1141
|
-
now;
|
|
1142
|
-
versionlessPublishQuiescenceMs;
|
|
1143
1178
|
constructor(sendNotification, clearDiagnostics, options = {}) {
|
|
1144
1179
|
this.sendNotification = sendNotification;
|
|
1145
1180
|
this.clearDiagnostics = clearDiagnostics;
|
|
1146
|
-
this.
|
|
1181
|
+
this.openDocuments = new Map;
|
|
1182
|
+
this.openByUri = new Map;
|
|
1183
|
+
this.openPromises = new Map;
|
|
1184
|
+
this.timerProvider = options.timerProvider ?? {
|
|
1185
|
+
now: options.now ?? (() => Date.now()),
|
|
1186
|
+
setTimeout: (callback, delayMs) => setTimeout(callback, delayMs),
|
|
1187
|
+
clearTimeout: (handle) => clearTimeout(handle)
|
|
1188
|
+
};
|
|
1189
|
+
this.now = () => this.timerProvider.now();
|
|
1147
1190
|
this.versionlessPublishQuiescenceMs = options.versionlessPublishQuiescenceMs ?? DEFAULT_VERSIONLESS_PUBLISH_QUIESCENCE_MS;
|
|
1148
1191
|
}
|
|
1149
1192
|
async openFile(filePath) {
|
|
@@ -1165,7 +1208,7 @@ class WorkspaceDocumentState {
|
|
|
1165
1208
|
return this.openDocuments.get(canonicalPath(filePath))?.version;
|
|
1166
1209
|
}
|
|
1167
1210
|
getStoredDiagnostics(uri) {
|
|
1168
|
-
const state = this.openByUri.get(uri);
|
|
1211
|
+
const state = this.openByUri.get(normalizeDocumentUri(uri));
|
|
1169
1212
|
if (!state)
|
|
1170
1213
|
return [];
|
|
1171
1214
|
return state.lastPublish?.diagnostics ?? state.pullCache?.diagnostics ?? [];
|
|
@@ -1187,13 +1230,13 @@ class WorkspaceDocumentState {
|
|
|
1187
1230
|
return state !== undefined && state.uri === snapshot.uri && state.version === snapshot.version && state.generation === snapshot.documentGeneration;
|
|
1188
1231
|
}
|
|
1189
1232
|
getPullCache(snapshot) {
|
|
1190
|
-
const state = this.openByUri.get(snapshot.uri);
|
|
1233
|
+
const state = this.openByUri.get(normalizeDocumentUri(snapshot.uri));
|
|
1191
1234
|
if (!state?.pullCache || state.pullCache.documentVersion !== snapshot.version)
|
|
1192
1235
|
return null;
|
|
1193
1236
|
return state.pullCache;
|
|
1194
1237
|
}
|
|
1195
1238
|
recordPullDiagnostics(snapshot, report) {
|
|
1196
|
-
const state = this.openByUri.get(snapshot.uri);
|
|
1239
|
+
const state = this.openByUri.get(normalizeDocumentUri(snapshot.uri));
|
|
1197
1240
|
if (!state)
|
|
1198
1241
|
return;
|
|
1199
1242
|
state.pullCache = {
|
|
@@ -1203,7 +1246,7 @@ class WorkspaceDocumentState {
|
|
|
1203
1246
|
};
|
|
1204
1247
|
}
|
|
1205
1248
|
recordPublishedDiagnostics(params) {
|
|
1206
|
-
const state = this.openByUri.get(params.uri);
|
|
1249
|
+
const state = this.openByUri.get(normalizeDocumentUri(params.uri));
|
|
1207
1250
|
if (!state)
|
|
1208
1251
|
return;
|
|
1209
1252
|
state.publishGeneration += 1;
|
|
@@ -1217,7 +1260,7 @@ class WorkspaceDocumentState {
|
|
|
1217
1260
|
this.notifyWaiters(state);
|
|
1218
1261
|
}
|
|
1219
1262
|
resolvePushDiagnostics(snapshot) {
|
|
1220
|
-
const state = this.openByUri.get(snapshot.uri);
|
|
1263
|
+
const state = this.openByUri.get(normalizeDocumentUri(snapshot.uri));
|
|
1221
1264
|
if (!state?.lastPublish)
|
|
1222
1265
|
return { status: "missing" };
|
|
1223
1266
|
const publish = state.lastPublish;
|
|
@@ -1231,7 +1274,7 @@ class WorkspaceDocumentState {
|
|
|
1231
1274
|
return waitMs === 0 ? { status: "ready", diagnostics: publish.diagnostics } : { status: "wait", waitMs };
|
|
1232
1275
|
}
|
|
1233
1276
|
waitForDiagnosticsActivity(snapshot, timeoutMs) {
|
|
1234
|
-
const state = this.openByUri.get(snapshot.uri);
|
|
1277
|
+
const state = this.openByUri.get(normalizeDocumentUri(snapshot.uri));
|
|
1235
1278
|
if (!state || timeoutMs <= 0)
|
|
1236
1279
|
return Promise.resolve();
|
|
1237
1280
|
return new Promise((resolveActivity) => {
|
|
@@ -1240,11 +1283,11 @@ class WorkspaceDocumentState {
|
|
|
1240
1283
|
if (settled)
|
|
1241
1284
|
return;
|
|
1242
1285
|
settled = true;
|
|
1243
|
-
clearTimeout(timer);
|
|
1286
|
+
this.timerProvider.clearTimeout(timer);
|
|
1244
1287
|
state.waiters.delete(finish);
|
|
1245
1288
|
resolveActivity();
|
|
1246
1289
|
};
|
|
1247
|
-
const timer = setTimeout(finish, timeoutMs);
|
|
1290
|
+
const timer = this.timerProvider.setTimeout(finish, timeoutMs);
|
|
1248
1291
|
if (typeof timer.unref === "function")
|
|
1249
1292
|
timer.unref();
|
|
1250
1293
|
state.waiters.add(finish);
|
|
@@ -1352,7 +1395,7 @@ class WorkspaceDocumentState {
|
|
|
1352
1395
|
waiters: new Set
|
|
1353
1396
|
};
|
|
1354
1397
|
this.openDocuments.set(path, state);
|
|
1355
|
-
this.openByUri.set(state.uri, state);
|
|
1398
|
+
this.openByUri.set(normalizeDocumentUri(state.uri), state);
|
|
1356
1399
|
this.notifyWaiters(state);
|
|
1357
1400
|
await this.sendNotification("textDocument/didOpen", {
|
|
1358
1401
|
textDocument: { uri: state.uri, languageId: state.languageId, version: state.version, text }
|
|
@@ -1377,7 +1420,7 @@ class WorkspaceDocumentState {
|
|
|
1377
1420
|
}
|
|
1378
1421
|
async closeDocument(state) {
|
|
1379
1422
|
this.openDocuments.delete(state.path);
|
|
1380
|
-
this.openByUri.delete(state.uri);
|
|
1423
|
+
this.openByUri.delete(normalizeDocumentUri(state.uri));
|
|
1381
1424
|
this.clearDiagnostics(state.uri);
|
|
1382
1425
|
this.notifyWaiters(state);
|
|
1383
1426
|
await this.sendNotification("textDocument/didClose", { textDocument: { uri: state.uri } });
|
|
@@ -1406,13 +1449,11 @@ import { dirname, isAbsolute, relative as relative2, resolve as resolve2 } from
|
|
|
1406
1449
|
import { fileURLToPath } from "node:url";
|
|
1407
1450
|
|
|
1408
1451
|
class WorkspaceEditPathError extends Error {
|
|
1409
|
-
path;
|
|
1410
|
-
detail;
|
|
1411
|
-
name = "WorkspaceEditPathError";
|
|
1412
1452
|
constructor(path, detail) {
|
|
1413
1453
|
super(`${detail}: ${path}`);
|
|
1414
1454
|
this.path = path;
|
|
1415
1455
|
this.detail = detail;
|
|
1456
|
+
this.name = "WorkspaceEditPathError";
|
|
1416
1457
|
}
|
|
1417
1458
|
}
|
|
1418
1459
|
function isPathInsideWorkspace(filePath, workspaceRoot) {
|
|
@@ -1704,13 +1745,11 @@ function canonicalFingerprint(operations) {
|
|
|
1704
1745
|
|
|
1705
1746
|
// ../lsp-core/src/lsp/workspace-edit-types.ts
|
|
1706
1747
|
class WorkspaceEditValidationError extends Error {
|
|
1707
|
-
changeIndex;
|
|
1708
|
-
detail;
|
|
1709
|
-
name = "WorkspaceEditValidationError";
|
|
1710
1748
|
constructor(changeIndex, detail) {
|
|
1711
1749
|
super(`change ${changeIndex}: ${detail}`);
|
|
1712
1750
|
this.changeIndex = changeIndex;
|
|
1713
1751
|
this.detail = detail;
|
|
1752
|
+
this.name = "WorkspaceEditValidationError";
|
|
1714
1753
|
}
|
|
1715
1754
|
}
|
|
1716
1755
|
|
|
@@ -1796,14 +1835,14 @@ function parseSinglePathResource(input, kind) {
|
|
|
1796
1835
|
return;
|
|
1797
1836
|
}
|
|
1798
1837
|
if (kind === "create") {
|
|
1799
|
-
const
|
|
1838
|
+
const options = parseOptions(change["options"], ["overwrite", "ignoreIfExists"], changeIndex);
|
|
1800
1839
|
target.operations.push({
|
|
1801
1840
|
kind,
|
|
1802
1841
|
changeIndex,
|
|
1803
1842
|
path: resolvedPath.path,
|
|
1804
1843
|
reportedPath: resolvedPath.requestedPath,
|
|
1805
|
-
overwrite:
|
|
1806
|
-
ignoreIfExists:
|
|
1844
|
+
overwrite: options["overwrite"] ?? false,
|
|
1845
|
+
ignoreIfExists: options["ignoreIfExists"] ?? false,
|
|
1807
1846
|
followedSymbolicLink: resolvedPath.followedSymbolicLink
|
|
1808
1847
|
});
|
|
1809
1848
|
return;
|
|
@@ -2208,10 +2247,9 @@ function simulateDelete(operation, virtual) {
|
|
|
2208
2247
|
import { existsSync as existsSync4, lstatSync as lstatSync3, readdirSync as readdirSync2 } from "node:fs";
|
|
2209
2248
|
import { dirname as dirname3, resolve as resolve4 } from "node:path";
|
|
2210
2249
|
class WorkspaceSnapshotBuilder {
|
|
2211
|
-
workspaceRoot;
|
|
2212
|
-
snapshots = new Map;
|
|
2213
2250
|
constructor(workspaceRoot) {
|
|
2214
2251
|
this.workspaceRoot = workspaceRoot;
|
|
2252
|
+
this.snapshots = new Map;
|
|
2215
2253
|
}
|
|
2216
2254
|
build(operations) {
|
|
2217
2255
|
this.add(this.workspaceRoot, false);
|
|
@@ -2255,8 +2293,10 @@ function snapshotOperations(operations, workspaceRoot) {
|
|
|
2255
2293
|
|
|
2256
2294
|
// ../lsp-core/src/lsp/workspace-edit-plan.ts
|
|
2257
2295
|
class PlanPathIndex {
|
|
2258
|
-
|
|
2259
|
-
|
|
2296
|
+
constructor() {
|
|
2297
|
+
this.firstChangeByPath = new Map;
|
|
2298
|
+
this.reportedPathByCanonical = new Map;
|
|
2299
|
+
}
|
|
2260
2300
|
build(operations) {
|
|
2261
2301
|
for (const operation of operations) {
|
|
2262
2302
|
switch (operation.kind) {
|
|
@@ -2272,11 +2312,11 @@ class PlanPathIndex {
|
|
|
2272
2312
|
}
|
|
2273
2313
|
}
|
|
2274
2314
|
}
|
|
2275
|
-
add(path,
|
|
2315
|
+
add(path, reportedPath, changeIndex) {
|
|
2276
2316
|
if (!this.firstChangeByPath.has(path))
|
|
2277
2317
|
this.firstChangeByPath.set(path, changeIndex);
|
|
2278
2318
|
if (!this.reportedPathByCanonical.has(path))
|
|
2279
|
-
this.reportedPathByCanonical.set(path,
|
|
2319
|
+
this.reportedPathByCanonical.set(path, reportedPath);
|
|
2280
2320
|
}
|
|
2281
2321
|
}
|
|
2282
2322
|
function fingerprintWorkspaceEdit(edit, workspaceRoot) {
|
|
@@ -2345,14 +2385,11 @@ function isRecord3(value) {
|
|
|
2345
2385
|
}
|
|
2346
2386
|
|
|
2347
2387
|
class WorkspaceMutationController {
|
|
2348
|
-
workspaceRoot;
|
|
2349
|
-
documents;
|
|
2350
|
-
activeLease = null;
|
|
2351
|
-
nextLeaseId = 1;
|
|
2352
|
-
io;
|
|
2353
2388
|
constructor(workspaceRoot, documents) {
|
|
2354
2389
|
this.workspaceRoot = workspaceRoot;
|
|
2355
2390
|
this.documents = documents;
|
|
2391
|
+
this.activeLease = null;
|
|
2392
|
+
this.nextLeaseId = 1;
|
|
2356
2393
|
}
|
|
2357
2394
|
setIo(io) {
|
|
2358
2395
|
this.io = io;
|
|
@@ -2391,8 +2428,8 @@ class WorkspaceMutationController {
|
|
|
2391
2428
|
};
|
|
2392
2429
|
}
|
|
2393
2430
|
lease.phase = "applying";
|
|
2394
|
-
lease.applyCompletion = new Promise((
|
|
2395
|
-
lease.resolveApply =
|
|
2431
|
+
lease.applyCompletion = new Promise((resolve) => {
|
|
2432
|
+
lease.resolveApply = resolve;
|
|
2396
2433
|
});
|
|
2397
2434
|
const edit = isRecord3(params) ? params["edit"] : undefined;
|
|
2398
2435
|
const record = edit === undefined ? { fingerprint: null, result: failure("workspace/applyEdit params.edit is required", 0) } : await this.applyEdit(edit, lease);
|
|
@@ -2465,14 +2502,12 @@ var DIAGNOSTICS_FRESHNESS_TIMEOUT_MS = 3000;
|
|
|
2465
2502
|
var VERSIONLESS_PUBLISH_QUIESCENCE_MS = 250;
|
|
2466
2503
|
|
|
2467
2504
|
class LspClient extends LspClientConnection {
|
|
2468
|
-
diagnosticPullErrors = [];
|
|
2469
|
-
documents;
|
|
2470
|
-
workspaceMutations;
|
|
2471
|
-
diagnosticsFreshnessTimeoutMs;
|
|
2472
2505
|
constructor(root, server, options = {}) {
|
|
2473
2506
|
super(root, server, options);
|
|
2507
|
+
this.diagnosticPullErrors = [];
|
|
2474
2508
|
this.diagnosticsFreshnessTimeoutMs = options.diagnosticsFreshnessTimeoutMs ?? DIAGNOSTICS_FRESHNESS_TIMEOUT_MS;
|
|
2475
2509
|
this.documents = new WorkspaceDocumentState((method, params) => this.sendNotification(method, params), (uri) => this.diagnosticsStore.delete(uri), {
|
|
2510
|
+
timerProvider: this.timerProvider,
|
|
2476
2511
|
versionlessPublishQuiescenceMs: options.versionlessPublishQuiescenceMs ?? VERSIONLESS_PUBLISH_QUIESCENCE_MS
|
|
2477
2512
|
});
|
|
2478
2513
|
this.workspaceMutations = new WorkspaceMutationController(root, this.documents);
|
|
@@ -2525,6 +2560,18 @@ class LspClient extends LspClientConnection {
|
|
|
2525
2560
|
textDocument: { uri: pathToFileURL3(absPath).href }
|
|
2526
2561
|
}, options);
|
|
2527
2562
|
}
|
|
2563
|
+
async formatDocument(filePath, options, signal) {
|
|
2564
|
+
if (!this.isDocumentFormattingSupported())
|
|
2565
|
+
return null;
|
|
2566
|
+
const absPath = this.resolveWorkspacePath(filePath);
|
|
2567
|
+
await this.openFile(absPath);
|
|
2568
|
+
const requestOptions = signal === undefined ? {} : { signal };
|
|
2569
|
+
const edits = await this.sendRequest("textDocument/formatting", {
|
|
2570
|
+
textDocument: { uri: pathToFileURL3(absPath).href },
|
|
2571
|
+
options
|
|
2572
|
+
}, requestOptions);
|
|
2573
|
+
return edits ?? [];
|
|
2574
|
+
}
|
|
2528
2575
|
async workspaceSymbols(query, signal) {
|
|
2529
2576
|
const options = signal === undefined ? {} : { signal };
|
|
2530
2577
|
return this.sendRequest("workspace/symbol", { query }, options);
|
|
@@ -2564,7 +2611,7 @@ class LspClient extends LspClientConnection {
|
|
|
2564
2611
|
const absPath = this.resolveWorkspacePath(filePath);
|
|
2565
2612
|
const uri = pathToFileURL3(absPath).href;
|
|
2566
2613
|
await this.openFile(absPath);
|
|
2567
|
-
const deadlineAt =
|
|
2614
|
+
const deadlineAt = this.timerProvider.now() + this.diagnosticsFreshnessTimeoutMs;
|
|
2568
2615
|
for (;; ) {
|
|
2569
2616
|
signal?.throwIfAborted();
|
|
2570
2617
|
const snapshot = this.documents.captureDiagnosticSnapshot(absPath);
|
|
@@ -2577,13 +2624,13 @@ class LspClient extends LspClientConnection {
|
|
|
2577
2624
|
if (!pushFallbackOnly) {
|
|
2578
2625
|
const cached = this.documents.getPullCache(snapshot);
|
|
2579
2626
|
try {
|
|
2580
|
-
const
|
|
2581
|
-
if (
|
|
2627
|
+
const remainingMs = deadlineAt - this.timerProvider.now();
|
|
2628
|
+
if (remainingMs <= 0)
|
|
2582
2629
|
return this.freshnessTimeout(absPath);
|
|
2583
2630
|
const result = await this.sendRequest("textDocument/diagnostic", {
|
|
2584
2631
|
textDocument: { uri },
|
|
2585
2632
|
...cached?.resultId === undefined ? {} : { previousResultId: cached.resultId }
|
|
2586
|
-
}, { timeoutMs:
|
|
2633
|
+
}, { timeoutMs: remainingMs, ...signal === undefined ? {} : { signal } });
|
|
2587
2634
|
if (!this.documents.isCurrentSnapshot(snapshot))
|
|
2588
2635
|
continue;
|
|
2589
2636
|
const report = this.parseDiagnosticPullReport(result);
|
|
@@ -2612,7 +2659,7 @@ class LspClient extends LspClientConnection {
|
|
|
2612
2659
|
}
|
|
2613
2660
|
if (!pushFallbackOnly)
|
|
2614
2661
|
continue;
|
|
2615
|
-
const remainingMs = deadlineAt -
|
|
2662
|
+
const remainingMs = deadlineAt - this.timerProvider.now();
|
|
2616
2663
|
if (remainingMs <= 0) {
|
|
2617
2664
|
if (!this.isDiagnosticPullSupported() && snapshot.publishGeneration === 0) {
|
|
2618
2665
|
const cached = this.documents.getPullCache(snapshot);
|
|
@@ -2664,7 +2711,7 @@ function waitForDiagnosticsActivity(wait, signal) {
|
|
|
2664
2711
|
return wait;
|
|
2665
2712
|
if (signal.aborted)
|
|
2666
2713
|
return Promise.reject(abortError2(signal));
|
|
2667
|
-
return new Promise((
|
|
2714
|
+
return new Promise((resolve, reject) => {
|
|
2668
2715
|
const onAbort = () => {
|
|
2669
2716
|
signal.removeEventListener("abort", onAbort);
|
|
2670
2717
|
reject(abortError2(signal));
|
|
@@ -2672,7 +2719,7 @@ function waitForDiagnosticsActivity(wait, signal) {
|
|
|
2672
2719
|
signal.addEventListener("abort", onAbort, { once: true });
|
|
2673
2720
|
wait.then(() => {
|
|
2674
2721
|
signal.removeEventListener("abort", onAbort);
|
|
2675
|
-
|
|
2722
|
+
resolve();
|
|
2676
2723
|
}, (error) => {
|
|
2677
2724
|
signal.removeEventListener("abort", onAbort);
|
|
2678
2725
|
reject(error);
|
|
@@ -2740,7 +2787,7 @@ async function stopClientBestEffort(client) {
|
|
|
2740
2787
|
function awaitWithSignal(promise, signal) {
|
|
2741
2788
|
if (!signal)
|
|
2742
2789
|
return promise;
|
|
2743
|
-
return new Promise((
|
|
2790
|
+
return new Promise((resolve, reject) => {
|
|
2744
2791
|
let settled = false;
|
|
2745
2792
|
const onAbort = () => {
|
|
2746
2793
|
if (settled)
|
|
@@ -2758,7 +2805,7 @@ function awaitWithSignal(promise, signal) {
|
|
|
2758
2805
|
return;
|
|
2759
2806
|
settled = true;
|
|
2760
2807
|
signal.removeEventListener("abort", onAbort);
|
|
2761
|
-
|
|
2808
|
+
resolve(value);
|
|
2762
2809
|
}, (err) => {
|
|
2763
2810
|
if (settled)
|
|
2764
2811
|
return;
|
|
@@ -2770,18 +2817,16 @@ function awaitWithSignal(promise, signal) {
|
|
|
2770
2817
|
}
|
|
2771
2818
|
|
|
2772
2819
|
class LspManager {
|
|
2773
|
-
clients = new Map;
|
|
2774
|
-
reaperHandle = null;
|
|
2775
|
-
signalDisposer = null;
|
|
2776
|
-
disposed = false;
|
|
2777
|
-
idleTimeoutMs;
|
|
2778
|
-
initTimeoutMs;
|
|
2779
|
-
reaperIntervalMs;
|
|
2780
|
-
clientFactory;
|
|
2781
|
-
now;
|
|
2782
2820
|
constructor(options = {}) {
|
|
2821
|
+
this.clients = new Map;
|
|
2822
|
+
this.pendingStops = new Map;
|
|
2823
|
+
this.respawnBudgets = new Map;
|
|
2824
|
+
this.reaperHandle = null;
|
|
2825
|
+
this.signalDisposer = null;
|
|
2826
|
+
this.disposed = false;
|
|
2783
2827
|
this.idleTimeoutMs = options.idleTimeoutMs ?? IDLE_TIMEOUT_MS;
|
|
2784
2828
|
this.initTimeoutMs = options.initTimeoutMs ?? INIT_TIMEOUT_MS;
|
|
2829
|
+
this.maxResidentClients = options.maxResidentClients ?? MAX_RESIDENT_CLIENTS;
|
|
2785
2830
|
this.reaperIntervalMs = options.reaperIntervalMs ?? REAPER_INTERVAL_MS;
|
|
2786
2831
|
this.clientFactory = options.clientFactory ?? ((root, server) => new LspClient(root, server));
|
|
2787
2832
|
this.now = options.now ?? (() => Date.now());
|
|
@@ -2801,24 +2846,79 @@ class LspManager {
|
|
|
2801
2846
|
getKey(root, serverId) {
|
|
2802
2847
|
return `${root}::${serverId}`;
|
|
2803
2848
|
}
|
|
2849
|
+
tombstoneStop(key, client) {
|
|
2850
|
+
const stop = stopClientBestEffort(client);
|
|
2851
|
+
this.pendingStops.set(key, stop);
|
|
2852
|
+
stop.finally(() => {
|
|
2853
|
+
if (this.pendingStops.get(key) === stop) {
|
|
2854
|
+
this.pendingStops.delete(key);
|
|
2855
|
+
}
|
|
2856
|
+
});
|
|
2857
|
+
return stop;
|
|
2858
|
+
}
|
|
2859
|
+
recordDeadGeneration(key) {
|
|
2860
|
+
let budget = this.respawnBudgets.get(key);
|
|
2861
|
+
if (budget === undefined) {
|
|
2862
|
+
budget = { deadGenerations: 0, exhaustedAt: null };
|
|
2863
|
+
this.respawnBudgets.set(key, budget);
|
|
2864
|
+
}
|
|
2865
|
+
budget.deadGenerations += 1;
|
|
2866
|
+
}
|
|
2867
|
+
markHealthyGeneration(key) {
|
|
2868
|
+
this.respawnBudgets.delete(key);
|
|
2869
|
+
}
|
|
2870
|
+
ensureRespawnAllowed(key, root, serverId) {
|
|
2871
|
+
const budget = this.respawnBudgets.get(key);
|
|
2872
|
+
if (budget === undefined || budget.deadGenerations < CLIENT_RESPAWN_RETRY_LIMIT)
|
|
2873
|
+
return;
|
|
2874
|
+
if (budget.exhaustedAt === null) {
|
|
2875
|
+
budget.exhaustedAt = this.now();
|
|
2876
|
+
throw new LspClientRespawnBudgetExceededError(serverId, root, CLIENT_RESPAWN_RETRY_LIMIT);
|
|
2877
|
+
}
|
|
2878
|
+
if (this.now() - budget.exhaustedAt < CLIENT_RESPAWN_COOLDOWN_MS) {
|
|
2879
|
+
throw new LspClientRespawnBudgetExceededError(serverId, root, CLIENT_RESPAWN_RETRY_LIMIT);
|
|
2880
|
+
}
|
|
2881
|
+
budget.deadGenerations = 0;
|
|
2882
|
+
budget.exhaustedAt = null;
|
|
2883
|
+
}
|
|
2804
2884
|
reapStale() {
|
|
2805
2885
|
const t = this.now();
|
|
2806
2886
|
for (const [key, managed] of this.clients) {
|
|
2807
2887
|
if (managed.isInitializing && managed.initializingSince !== null && t - managed.initializingSince > this.initTimeoutMs) {
|
|
2808
|
-
stopClientBestEffort(managed.client);
|
|
2809
2888
|
this.clients.delete(key);
|
|
2889
|
+
this.tombstoneStop(key, managed.client);
|
|
2810
2890
|
continue;
|
|
2811
2891
|
}
|
|
2812
2892
|
if (!managed.isInitializing && managed.refCount === 0 && managed.pendingWaiters === 0 && t - managed.lastUsedAt > this.idleTimeoutMs) {
|
|
2813
|
-
stopClientBestEffort(managed.client);
|
|
2814
2893
|
this.clients.delete(key);
|
|
2894
|
+
this.tombstoneStop(key, managed.client);
|
|
2895
|
+
}
|
|
2896
|
+
}
|
|
2897
|
+
}
|
|
2898
|
+
evictForAdmission() {
|
|
2899
|
+
while (this.clients.size >= this.maxResidentClients) {
|
|
2900
|
+
const victim = this.leastRecentlyUsedIdleClient();
|
|
2901
|
+
if (!victim)
|
|
2902
|
+
return;
|
|
2903
|
+
this.clients.delete(victim.key);
|
|
2904
|
+
this.tombstoneStop(victim.key, victim.managed.client);
|
|
2905
|
+
}
|
|
2906
|
+
}
|
|
2907
|
+
leastRecentlyUsedIdleClient() {
|
|
2908
|
+
let candidate = null;
|
|
2909
|
+
for (const [key, managed] of this.clients) {
|
|
2910
|
+
if (managed.refCount > 0 || managed.pendingWaiters > 0 || managed.isInitializing)
|
|
2911
|
+
continue;
|
|
2912
|
+
if (candidate === null || managed.lastUsedAt < candidate.managed.lastUsedAt) {
|
|
2913
|
+
candidate = { key, managed };
|
|
2815
2914
|
}
|
|
2816
2915
|
}
|
|
2916
|
+
return candidate;
|
|
2817
2917
|
}
|
|
2818
2918
|
async tryDeleteIfOrphaned(key, managed) {
|
|
2819
2919
|
if (managed.refCount === 0 && managed.pendingWaiters === 0 && !managed.isInitializing && this.clients.get(key) === managed) {
|
|
2820
2920
|
this.clients.delete(key);
|
|
2821
|
-
await
|
|
2921
|
+
await this.tombstoneStop(key, managed.client);
|
|
2822
2922
|
}
|
|
2823
2923
|
}
|
|
2824
2924
|
async getClient(root, server, signal) {
|
|
@@ -2827,12 +2927,22 @@ class LspManager {
|
|
|
2827
2927
|
}
|
|
2828
2928
|
signal?.throwIfAborted();
|
|
2829
2929
|
const key = this.getKey(root, server.id);
|
|
2930
|
+
for (;; ) {
|
|
2931
|
+
const pendingStop = this.pendingStops.get(key);
|
|
2932
|
+
if (pendingStop === undefined)
|
|
2933
|
+
break;
|
|
2934
|
+
await awaitWithSignal(pendingStop, signal);
|
|
2935
|
+
signal?.throwIfAborted();
|
|
2936
|
+
}
|
|
2937
|
+
if (this.disposed) {
|
|
2938
|
+
throw new Error("LspManager has been disposed");
|
|
2939
|
+
}
|
|
2830
2940
|
let managed = this.clients.get(key);
|
|
2831
2941
|
if (managed) {
|
|
2832
2942
|
const t = this.now();
|
|
2833
2943
|
if (managed.isInitializing && managed.initializingSince !== null && t - managed.initializingSince > this.initTimeoutMs) {
|
|
2834
|
-
await stopClientBestEffort(managed.client);
|
|
2835
2944
|
this.clients.delete(key);
|
|
2945
|
+
await this.tombstoneStop(key, managed.client);
|
|
2836
2946
|
managed = undefined;
|
|
2837
2947
|
}
|
|
2838
2948
|
}
|
|
@@ -2853,14 +2963,20 @@ class LspManager {
|
|
|
2853
2963
|
signal.throwIfAborted();
|
|
2854
2964
|
}
|
|
2855
2965
|
if (!managed.client.isAlive()) {
|
|
2856
|
-
|
|
2857
|
-
this.clients.
|
|
2966
|
+
this.recordDeadGeneration(key);
|
|
2967
|
+
if (this.clients.get(key) === managed) {
|
|
2968
|
+
this.clients.delete(key);
|
|
2969
|
+
}
|
|
2970
|
+
await this.tombstoneStop(key, managed.client);
|
|
2858
2971
|
return this.getClient(root, server, signal);
|
|
2859
2972
|
}
|
|
2973
|
+
this.markHealthyGeneration(key);
|
|
2860
2974
|
managed.refCount++;
|
|
2861
2975
|
managed.lastUsedAt = this.now();
|
|
2862
2976
|
return managed.client;
|
|
2863
2977
|
}
|
|
2978
|
+
this.evictForAdmission();
|
|
2979
|
+
this.ensureRespawnAllowed(key, root, server.id);
|
|
2864
2980
|
const client = this.clientFactory(root, server);
|
|
2865
2981
|
const initStartedAt = this.now();
|
|
2866
2982
|
const initPromise = (async () => {
|
|
@@ -2884,7 +3000,7 @@ class LspManager {
|
|
|
2884
3000
|
if (this.clients.get(key) === newManaged) {
|
|
2885
3001
|
this.clients.delete(key);
|
|
2886
3002
|
}
|
|
2887
|
-
await
|
|
3003
|
+
await this.tombstoneStop(key, client);
|
|
2888
3004
|
throw err;
|
|
2889
3005
|
}
|
|
2890
3006
|
newManaged.pendingWaiters--;
|
|
@@ -2895,6 +3011,15 @@ class LspManager {
|
|
|
2895
3011
|
await this.tryDeleteIfOrphaned(key, newManaged);
|
|
2896
3012
|
signal.throwIfAborted();
|
|
2897
3013
|
}
|
|
3014
|
+
if (!client.isAlive()) {
|
|
3015
|
+
this.recordDeadGeneration(key);
|
|
3016
|
+
if (this.clients.get(key) === newManaged) {
|
|
3017
|
+
this.clients.delete(key);
|
|
3018
|
+
}
|
|
3019
|
+
await this.tombstoneStop(key, client);
|
|
3020
|
+
return this.getClient(root, server, signal);
|
|
3021
|
+
}
|
|
3022
|
+
this.markHealthyGeneration(key);
|
|
2898
3023
|
newManaged.refCount++;
|
|
2899
3024
|
newManaged.lastUsedAt = this.now();
|
|
2900
3025
|
return client;
|
|
@@ -2915,14 +3040,20 @@ class LspManager {
|
|
|
2915
3040
|
if (client && managed.client !== client)
|
|
2916
3041
|
return;
|
|
2917
3042
|
this.clients.delete(key);
|
|
2918
|
-
|
|
3043
|
+
this.tombstoneStop(key, managed.client);
|
|
2919
3044
|
}
|
|
2920
3045
|
warmupClient(root, server) {
|
|
2921
3046
|
if (this.disposed)
|
|
2922
3047
|
return;
|
|
2923
3048
|
const key = this.getKey(root, server.id);
|
|
2924
|
-
if (this.clients.has(key))
|
|
3049
|
+
if (this.clients.has(key) || this.pendingStops.has(key))
|
|
2925
3050
|
return;
|
|
3051
|
+
this.evictForAdmission();
|
|
3052
|
+
try {
|
|
3053
|
+
this.ensureRespawnAllowed(key, root, server.id);
|
|
3054
|
+
} catch {
|
|
3055
|
+
return;
|
|
3056
|
+
}
|
|
2926
3057
|
const client = this.clientFactory(root, server);
|
|
2927
3058
|
const initStartedAt = this.now();
|
|
2928
3059
|
const initPromise = (async () => {
|
|
@@ -2948,7 +3079,7 @@ class LspManager {
|
|
|
2948
3079
|
if (this.clients.get(key) === managed) {
|
|
2949
3080
|
this.clients.delete(key);
|
|
2950
3081
|
}
|
|
2951
|
-
|
|
3082
|
+
this.tombstoneStop(key, client);
|
|
2952
3083
|
});
|
|
2953
3084
|
}
|
|
2954
3085
|
isServerInitializing(root, serverId) {
|
|
@@ -2992,8 +3123,11 @@ class LspManager {
|
|
|
2992
3123
|
for (const managed of this.clients.values()) {
|
|
2993
3124
|
stopPromises.push(stopClientBestEffort(managed.client));
|
|
2994
3125
|
}
|
|
3126
|
+
const tombstonedStops = [...this.pendingStops.values()];
|
|
2995
3127
|
this.clients.clear();
|
|
2996
|
-
|
|
3128
|
+
this.respawnBudgets.clear();
|
|
3129
|
+
await Promise.allSettled([...stopPromises, ...tombstonedStops]);
|
|
3130
|
+
this.pendingStops.clear();
|
|
2997
3131
|
}
|
|
2998
3132
|
}
|
|
2999
3133
|
var _defaultInstance = null;
|
|
@@ -3013,7 +3147,7 @@ async function disposeDefaultLspManager() {
|
|
|
3013
3147
|
// src/daemon-client.ts
|
|
3014
3148
|
import { connect } from "node:net";
|
|
3015
3149
|
import { homedir as homedir3 } from "node:os";
|
|
3016
|
-
import { join as
|
|
3150
|
+
import { join as join8 } from "node:path";
|
|
3017
3151
|
|
|
3018
3152
|
// ../lsp-core/src/request-context.ts
|
|
3019
3153
|
import { AsyncLocalStorage } from "node:async_hooks";
|
|
@@ -3022,18 +3156,17 @@ import { homedir } from "node:os";
|
|
|
3022
3156
|
import { basename as basename2, delimiter as delimiter2, dirname as dirname4, isAbsolute as isAbsolute2, join as join2, relative as relative4, resolve as resolve6 } from "node:path";
|
|
3023
3157
|
|
|
3024
3158
|
class LspRequestContextParseError extends Error {
|
|
3025
|
-
code;
|
|
3026
|
-
name = "LspRequestContextParseError";
|
|
3027
3159
|
constructor(code, message) {
|
|
3028
3160
|
super(message);
|
|
3029
3161
|
this.code = code;
|
|
3162
|
+
this.name = "LspRequestContextParseError";
|
|
3030
3163
|
}
|
|
3031
3164
|
}
|
|
3032
3165
|
|
|
3033
3166
|
class LspRequestContextUnavailableError extends Error {
|
|
3034
|
-
name = "LspRequestContextUnavailableError";
|
|
3035
3167
|
constructor() {
|
|
3036
3168
|
super("LSP request context is required. Standalone MCP startup must install one with runWithRequestContext(createStandaloneMcpRequestContext()).");
|
|
3169
|
+
this.name = "LspRequestContextUnavailableError";
|
|
3037
3170
|
}
|
|
3038
3171
|
}
|
|
3039
3172
|
var storage = new AsyncLocalStorage;
|
|
@@ -3053,7 +3186,7 @@ function contextCwd() {
|
|
|
3053
3186
|
}
|
|
3054
3187
|
function createStandaloneMcpRequestContext(input = {}) {
|
|
3055
3188
|
const env = input.env ?? process.env;
|
|
3056
|
-
const cwd = canonicalCwd(input.cwd ?? process.cwd());
|
|
3189
|
+
const cwd = canonicalCwd(input.cwd ?? env["LSP_TOOLS_MCP_CWD"] ?? process.cwd());
|
|
3057
3190
|
const home = input.homeDir ?? homedir();
|
|
3058
3191
|
const projectConfigPaths = translateProjectConfigEnv(env["LSP_TOOLS_MCP_PROJECT_CONFIG"], cwd);
|
|
3059
3192
|
const userConfigPath = translateHomeConfigEnv(env["LSP_TOOLS_MCP_USER_CONFIG"], home, ".codex/lsp-client.json");
|
|
@@ -3191,7 +3324,6 @@ function isPlainRecord(value) {
|
|
|
3191
3324
|
|
|
3192
3325
|
// src/daemon-request-error.ts
|
|
3193
3326
|
class DaemonRequestError extends Error {
|
|
3194
|
-
requestWritten;
|
|
3195
3327
|
constructor(message, requestWritten) {
|
|
3196
3328
|
super(message);
|
|
3197
3329
|
this.name = "DaemonRequestError";
|
|
@@ -3214,7 +3346,6 @@ class DaemonRequestCancelledError extends DaemonRequestError {
|
|
|
3214
3346
|
}
|
|
3215
3347
|
|
|
3216
3348
|
class DaemonRequestTimedOutError extends DaemonRequestError {
|
|
3217
|
-
timeoutMs;
|
|
3218
3349
|
constructor(requestWritten, timeoutMs) {
|
|
3219
3350
|
super("daemon request timed out", requestWritten);
|
|
3220
3351
|
this.name = "DaemonRequestTimedOutError";
|
|
@@ -3293,14 +3424,12 @@ var PROTOCOL_ERROR_CODE = -32002;
|
|
|
3293
3424
|
var AUTH_TOKEN_BYTES = 32;
|
|
3294
3425
|
|
|
3295
3426
|
class UnsafePrivateDirectoryError extends Error {
|
|
3296
|
-
path;
|
|
3297
|
-
reason;
|
|
3298
|
-
name = "UnsafePrivateDirectoryError";
|
|
3299
|
-
code = "unsafe_private_directory";
|
|
3300
3427
|
constructor(path, reason) {
|
|
3301
3428
|
super(`unsafe private directory ${path}: ${reason}`);
|
|
3302
3429
|
this.path = path;
|
|
3303
3430
|
this.reason = reason;
|
|
3431
|
+
this.name = "UnsafePrivateDirectoryError";
|
|
3432
|
+
this.code = "unsafe_private_directory";
|
|
3304
3433
|
}
|
|
3305
3434
|
}
|
|
3306
3435
|
function authEnvelope(token) {
|
|
@@ -3484,20 +3613,18 @@ var OMO_LSP_DAEMON_VERSION = "OMO_LSP_DAEMON_VERSION";
|
|
|
3484
3613
|
var DAEMON_VERSION_PATTERN = /^[A-Za-z0-9][A-Za-z0-9._+-]{0,127}$/;
|
|
3485
3614
|
|
|
3486
3615
|
class InvalidRuntimeOverrideError extends Error {
|
|
3487
|
-
code = "invalid_runtime_override";
|
|
3488
|
-
reason;
|
|
3489
3616
|
constructor(reason, message) {
|
|
3490
3617
|
super(message);
|
|
3618
|
+
this.code = "invalid_runtime_override";
|
|
3491
3619
|
this.name = "InvalidRuntimeOverrideError";
|
|
3492
3620
|
this.reason = reason;
|
|
3493
3621
|
}
|
|
3494
3622
|
}
|
|
3495
3623
|
|
|
3496
3624
|
class InvalidDaemonVersionError extends Error {
|
|
3497
|
-
code = "invalid_daemon_version";
|
|
3498
|
-
version;
|
|
3499
3625
|
constructor(version) {
|
|
3500
3626
|
super("LSP daemon version must match [A-Za-z0-9][A-Za-z0-9._+-]{0,127}");
|
|
3627
|
+
this.code = "invalid_daemon_version";
|
|
3501
3628
|
this.name = "InvalidDaemonVersionError";
|
|
3502
3629
|
this.version = version;
|
|
3503
3630
|
}
|
|
@@ -3543,10 +3670,9 @@ var requireFromHere = createRequire(import.meta.url);
|
|
|
3543
3670
|
var MAX_SOCKET_PATH_LENGTH = 100;
|
|
3544
3671
|
|
|
3545
3672
|
class InvalidDaemonDirectoryError extends Error {
|
|
3546
|
-
code = "invalid_daemon_directory";
|
|
3547
|
-
directory;
|
|
3548
3673
|
constructor(directory) {
|
|
3549
3674
|
super(`${OMO_LSP_DAEMON_DIR} must be an absolute path`);
|
|
3675
|
+
this.code = "invalid_daemon_directory";
|
|
3550
3676
|
this.name = "InvalidDaemonDirectoryError";
|
|
3551
3677
|
this.directory = directory;
|
|
3552
3678
|
}
|
|
@@ -3700,7 +3826,7 @@ async function probeDaemon(paths, timeoutMs = PROBE_TIMEOUT_MS, signal) {
|
|
|
3700
3826
|
return await pingDaemon(paths, token, timeoutMs, signal) !== null;
|
|
3701
3827
|
}
|
|
3702
3828
|
function pingDaemon(paths, token, timeoutMs = PROBE_TIMEOUT_MS, signal) {
|
|
3703
|
-
return new Promise((
|
|
3829
|
+
return new Promise((resolve) => {
|
|
3704
3830
|
const socket = new Socket;
|
|
3705
3831
|
let settled = false;
|
|
3706
3832
|
let timer;
|
|
@@ -3712,7 +3838,7 @@ function pingDaemon(paths, token, timeoutMs = PROBE_TIMEOUT_MS, signal) {
|
|
|
3712
3838
|
clearTimeout(timer);
|
|
3713
3839
|
signal?.removeEventListener("abort", onAbort);
|
|
3714
3840
|
socket.destroy();
|
|
3715
|
-
|
|
3841
|
+
resolve(value);
|
|
3716
3842
|
};
|
|
3717
3843
|
const onAbort = () => finish(null);
|
|
3718
3844
|
const decoder = createLineDecoder((message) => {
|
|
@@ -3735,13 +3861,17 @@ function pingDaemon(paths, token, timeoutMs = PROBE_TIMEOUT_MS, signal) {
|
|
|
3735
3861
|
socket.connect(paths.socket);
|
|
3736
3862
|
});
|
|
3737
3863
|
}
|
|
3738
|
-
function spawnDaemonProcess(paths) {
|
|
3864
|
+
function spawnDaemonProcess(paths, deps = {}) {
|
|
3739
3865
|
mkdirSync2(dirname6(paths.log), { recursive: true });
|
|
3740
3866
|
const logFd = openSync2(paths.log, "a");
|
|
3741
3867
|
try {
|
|
3742
|
-
const
|
|
3868
|
+
const spawnDaemonChild = deps.spawn ?? spawn2;
|
|
3869
|
+
const executable = deps.resolveExecutable?.() ?? resolveDaemonNodeExecutable();
|
|
3870
|
+
const child = spawnDaemonChild(executable, [paths.cliPath, "daemon"], {
|
|
3743
3871
|
detached: true,
|
|
3744
|
-
stdio: ["ignore", logFd, logFd]
|
|
3872
|
+
stdio: ["ignore", logFd, logFd],
|
|
3873
|
+
windowsHide: true,
|
|
3874
|
+
env: { ...process.env, BUN_BE_BUN: "1" }
|
|
3745
3875
|
});
|
|
3746
3876
|
child.once("spawn", () => closeSync2(logFd));
|
|
3747
3877
|
child.once("error", (error) => {
|
|
@@ -3771,7 +3901,7 @@ function defaultEnsureDaemonDeps() {
|
|
|
3771
3901
|
};
|
|
3772
3902
|
}
|
|
3773
3903
|
function sleepWithSignal(ms, signal) {
|
|
3774
|
-
return new Promise((
|
|
3904
|
+
return new Promise((resolve) => {
|
|
3775
3905
|
let settled = false;
|
|
3776
3906
|
const finish = () => {
|
|
3777
3907
|
if (settled)
|
|
@@ -3779,7 +3909,7 @@ function sleepWithSignal(ms, signal) {
|
|
|
3779
3909
|
settled = true;
|
|
3780
3910
|
clearTimeout(timer);
|
|
3781
3911
|
signal?.removeEventListener("abort", finish);
|
|
3782
|
-
|
|
3912
|
+
resolve();
|
|
3783
3913
|
};
|
|
3784
3914
|
const timer = setTimeout(finish, ms);
|
|
3785
3915
|
if (signal?.aborted) {
|
|
@@ -3794,7 +3924,7 @@ function awaitWithSignal2(promise, signal) {
|
|
|
3794
3924
|
return promise;
|
|
3795
3925
|
if (signal.aborted)
|
|
3796
3926
|
return Promise.reject(abortError3(signal));
|
|
3797
|
-
return new Promise((
|
|
3927
|
+
return new Promise((resolve, reject) => {
|
|
3798
3928
|
let settled = false;
|
|
3799
3929
|
const finish = (run) => {
|
|
3800
3930
|
if (settled)
|
|
@@ -3805,7 +3935,7 @@ function awaitWithSignal2(promise, signal) {
|
|
|
3805
3935
|
};
|
|
3806
3936
|
const onAbort = () => finish(() => reject(abortError3(signal)));
|
|
3807
3937
|
signal.addEventListener("abort", onAbort, { once: true });
|
|
3808
|
-
promise.then((value) => finish(() =>
|
|
3938
|
+
promise.then((value) => finish(() => resolve(value)), (error) => finish(() => reject(error)));
|
|
3809
3939
|
});
|
|
3810
3940
|
}
|
|
3811
3941
|
function throwIfAborted(signal) {
|
|
@@ -3834,18 +3964,18 @@ function parsePingResponse(message) {
|
|
|
3834
3964
|
return null;
|
|
3835
3965
|
if (!endpoint || typeof endpoint !== "object" || Array.isArray(endpoint))
|
|
3836
3966
|
return null;
|
|
3837
|
-
const
|
|
3967
|
+
const path = Reflect.get(endpoint, "path");
|
|
3838
3968
|
const kind = Reflect.get(endpoint, "kind");
|
|
3839
|
-
if (typeof
|
|
3969
|
+
if (typeof path !== "string")
|
|
3840
3970
|
return null;
|
|
3841
3971
|
if (kind === "windows")
|
|
3842
|
-
return { pid, nonce, startedAt, endpoint: { kind, path
|
|
3972
|
+
return { pid, nonce, startedAt, endpoint: { kind, path } };
|
|
3843
3973
|
if (kind === "missing")
|
|
3844
|
-
return { pid, nonce, startedAt, endpoint: { kind, path
|
|
3974
|
+
return { pid, nonce, startedAt, endpoint: { kind, path } };
|
|
3845
3975
|
const dev = Reflect.get(endpoint, "dev");
|
|
3846
3976
|
const ino = Reflect.get(endpoint, "ino");
|
|
3847
3977
|
if (kind === "unix" && typeof dev === "number" && typeof ino === "number") {
|
|
3848
|
-
return { pid, nonce, startedAt, endpoint: { kind, path
|
|
3978
|
+
return { pid, nonce, startedAt, endpoint: { kind, path, dev, ino } };
|
|
3849
3979
|
}
|
|
3850
3980
|
return null;
|
|
3851
3981
|
}
|
|
@@ -3893,7 +4023,7 @@ ${body}` : `${body}
|
|
|
3893
4023
|
await writeChunk(output, payload);
|
|
3894
4024
|
}
|
|
3895
4025
|
function writeChunk(output, chunk) {
|
|
3896
|
-
return new Promise((
|
|
4026
|
+
return new Promise((resolve, reject) => {
|
|
3897
4027
|
let settled = false;
|
|
3898
4028
|
const onError = (error) => {
|
|
3899
4029
|
if (settled)
|
|
@@ -3913,7 +4043,7 @@ function writeChunk(output, chunk) {
|
|
|
3913
4043
|
return;
|
|
3914
4044
|
}
|
|
3915
4045
|
output.removeListener("error", onError);
|
|
3916
|
-
|
|
4046
|
+
resolve();
|
|
3917
4047
|
});
|
|
3918
4048
|
} catch (error) {
|
|
3919
4049
|
output.removeListener("error", onError);
|
|
@@ -4022,6 +4152,7 @@ async function runJsonRpcStdioServer(config) {
|
|
|
4022
4152
|
const idleTimer = createIdleTimer(idleTimeoutMs, log, () => {
|
|
4023
4153
|
isClosed = true;
|
|
4024
4154
|
config.onIdleTimeout?.();
|
|
4155
|
+
config.input.destroy();
|
|
4025
4156
|
});
|
|
4026
4157
|
const watchdog = createParentWatchdog(config.parentWatchdog, (parentPid, pollIntervalMs) => {
|
|
4027
4158
|
isClosed = true;
|
|
@@ -4118,7 +4249,11 @@ function createParentWatchdog(config, onDeadParent) {
|
|
|
4118
4249
|
const probeAlive = config.probeAlive ?? isProcessAlive;
|
|
4119
4250
|
let fired = false;
|
|
4120
4251
|
const timer = setInterval(() => {
|
|
4121
|
-
if (fired
|
|
4252
|
+
if (fired)
|
|
4253
|
+
return;
|
|
4254
|
+
const alive = probeAlive(parentPid);
|
|
4255
|
+
config.onPoll?.(alive);
|
|
4256
|
+
if (alive)
|
|
4122
4257
|
return;
|
|
4123
4258
|
fired = true;
|
|
4124
4259
|
onDeadParent(parentPid, pollIntervalMs);
|
|
@@ -4153,60 +4288,55 @@ function createIdleTimer(idleTimeoutMs, log, onTimeout) {
|
|
|
4153
4288
|
};
|
|
4154
4289
|
}
|
|
4155
4290
|
// ../lsp-core/src/lsp/client-wrapper.ts
|
|
4156
|
-
import { existsSync as
|
|
4157
|
-
import { basename as basename3, dirname as
|
|
4291
|
+
import { existsSync as existsSync11, realpathSync as realpathSync5, statSync as statSync4 } from "node:fs";
|
|
4292
|
+
import { basename as basename3, dirname as dirname10, join as join5, resolve as resolve8 } from "node:path";
|
|
4158
4293
|
|
|
4159
|
-
// ../lsp-core/src/lsp/
|
|
4160
|
-
import { existsSync as existsSync7,
|
|
4161
|
-
import { dirname as dirname7 } from "node:path";
|
|
4162
|
-
|
|
4163
|
-
|
|
4164
|
-
|
|
4165
|
-
|
|
4166
|
-
|
|
4167
|
-
|
|
4168
|
-
|
|
4169
|
-
|
|
4170
|
-
|
|
4171
|
-
|
|
4172
|
-
|
|
4173
|
-
|
|
4294
|
+
// ../lsp-core/src/lsp/outside-context-workspace.ts
|
|
4295
|
+
import { existsSync as existsSync7, realpathSync as realpathSync4 } from "node:fs";
|
|
4296
|
+
import { dirname as dirname7, join as join3 } from "node:path";
|
|
4297
|
+
|
|
4298
|
+
// ../lsp-core/src/lsp/workspace-markers.ts
|
|
4299
|
+
var GIT_WORKSPACE_MARKER = ".git";
|
|
4300
|
+
var PROJECT_WORKSPACE_MARKERS = [
|
|
4301
|
+
"package.json",
|
|
4302
|
+
"pyproject.toml",
|
|
4303
|
+
"Cargo.toml",
|
|
4304
|
+
"go.mod",
|
|
4305
|
+
"pom.xml",
|
|
4306
|
+
"build.gradle"
|
|
4307
|
+
];
|
|
4308
|
+
var WORKSPACE_MARKERS = [GIT_WORKSPACE_MARKER, ...PROJECT_WORKSPACE_MARKERS];
|
|
4309
|
+
|
|
4310
|
+
// ../lsp-core/src/lsp/outside-context-workspace.ts
|
|
4311
|
+
function findWorkspaceRootOutsideContext(directory) {
|
|
4312
|
+
const marked = nearestMarkedAncestor(directory);
|
|
4313
|
+
if (marked !== undefined)
|
|
4314
|
+
return marked;
|
|
4315
|
+
return realpathSync4(nearestExistingAncestor(directory));
|
|
4316
|
+
}
|
|
4317
|
+
function nearestMarkedAncestor(directory) {
|
|
4318
|
+
let current = directory;
|
|
4319
|
+
for (;; ) {
|
|
4320
|
+
if (existsSync7(current) && WORKSPACE_MARKERS.some((marker) => existsSync7(join3(current, marker)))) {
|
|
4321
|
+
return realpathSync4(current);
|
|
4322
|
+
}
|
|
4323
|
+
const parent = dirname7(current);
|
|
4324
|
+
if (parent === current)
|
|
4325
|
+
return;
|
|
4326
|
+
current = parent;
|
|
4174
4327
|
}
|
|
4175
4328
|
}
|
|
4176
|
-
function
|
|
4177
|
-
|
|
4178
|
-
|
|
4179
|
-
|
|
4180
|
-
|
|
4181
|
-
|
|
4182
|
-
|
|
4183
|
-
}
|
|
4184
|
-
|
|
4185
|
-
return value === "declined" || value === "allowed";
|
|
4186
|
-
}
|
|
4187
|
-
function writeInstallDecisions(decisions) {
|
|
4188
|
-
const path2 = getInstallDecisionsPath();
|
|
4189
|
-
mkdirSync3(dirname7(path2), { recursive: true });
|
|
4190
|
-
const tmpPath = `${path2}.tmp`;
|
|
4191
|
-
writeFileSync2(tmpPath, `${JSON.stringify(decisions, null, 2)}
|
|
4192
|
-
`, "utf8");
|
|
4193
|
-
renameSync2(tmpPath, path2);
|
|
4194
|
-
}
|
|
4195
|
-
function isInstallDecisions(value) {
|
|
4196
|
-
return isRecord5(value) && Object.values(value).every(isInstallDecisionRecord);
|
|
4197
|
-
}
|
|
4198
|
-
function isInstallDecisionRecord(value) {
|
|
4199
|
-
if (!isRecord5(value))
|
|
4200
|
-
return false;
|
|
4201
|
-
return isInstallDecision(value["decision"]) && typeof value["decidedAt"] === "string";
|
|
4202
|
-
}
|
|
4203
|
-
function isRecord5(value) {
|
|
4204
|
-
return typeof value === "object" && value !== null && !Array.isArray(value);
|
|
4329
|
+
function nearestExistingAncestor(directory) {
|
|
4330
|
+
let current = directory;
|
|
4331
|
+
while (!existsSync7(current)) {
|
|
4332
|
+
const parent = dirname7(current);
|
|
4333
|
+
if (parent === current)
|
|
4334
|
+
return current;
|
|
4335
|
+
current = parent;
|
|
4336
|
+
}
|
|
4337
|
+
return current;
|
|
4205
4338
|
}
|
|
4206
4339
|
|
|
4207
|
-
// ../lsp-core/src/lsp/config-loader.ts
|
|
4208
|
-
import { existsSync as existsSync8, readFileSync as readFileSync5 } from "node:fs";
|
|
4209
|
-
|
|
4210
4340
|
// ../lsp-core/src/lsp/server-definitions.ts
|
|
4211
4341
|
var LSP_INSTALL_HINTS = {
|
|
4212
4342
|
typescript: "npm install -g typescript-language-server typescript",
|
|
@@ -4252,6 +4382,26 @@ var LSP_INSTALL_HINTS = {
|
|
|
4252
4382
|
julials: `julia -e 'using Pkg; Pkg.add("LanguageServer")'`,
|
|
4253
4383
|
razor: "Razor runs through the Roslyn language server (cohosting). " + "Install: dotnet tool install -g roslyn-language-server --prerelease (requires v5.8.0+). See https://github.com/dotnet/razor"
|
|
4254
4384
|
};
|
|
4385
|
+
var LSP_LOCAL_INSTALL_HINTS = {
|
|
4386
|
+
typescript: "bun add -d typescript-language-server typescript",
|
|
4387
|
+
vue: "bun add -d @vue/language-server",
|
|
4388
|
+
eslint: "bun add -d vscode-langservers-extracted",
|
|
4389
|
+
oxlint: "bun add -d oxlint",
|
|
4390
|
+
biome: "bun add -d @biomejs/biome",
|
|
4391
|
+
svelte: "bun add -d svelte-language-server",
|
|
4392
|
+
astro: "bun add -d @astrojs/language-server",
|
|
4393
|
+
bash: "bun add -d bash-language-server",
|
|
4394
|
+
"bash-ls": "bun add -d bash-language-server",
|
|
4395
|
+
"yaml-ls": "bun add -d yaml-language-server",
|
|
4396
|
+
php: "bun add -d intelephense",
|
|
4397
|
+
prisma: "bun add -d prisma",
|
|
4398
|
+
dockerfile: "bun add -d dockerfile-language-server-nodejs",
|
|
4399
|
+
pyright: "uv add --dev pyright",
|
|
4400
|
+
basedpyright: "uv add --dev basedpyright",
|
|
4401
|
+
ruff: "uv add --dev ruff",
|
|
4402
|
+
ty: "uv add --dev ty",
|
|
4403
|
+
"ruby-lsp": "bundle add ruby-lsp --group development"
|
|
4404
|
+
};
|
|
4255
4405
|
var BUILTIN_SERVERS = {
|
|
4256
4406
|
typescript: {
|
|
4257
4407
|
command: ["typescript-language-server", "--stdio"],
|
|
@@ -4354,18 +4504,67 @@ var BUILTIN_SERVERS = {
|
|
|
4354
4504
|
}
|
|
4355
4505
|
};
|
|
4356
4506
|
|
|
4507
|
+
// ../lsp-core/src/lsp/server-install-state.ts
|
|
4508
|
+
import { existsSync as existsSync8, mkdirSync as mkdirSync3, readFileSync as readFileSync4, renameSync as renameSync2, writeFileSync as writeFileSync2 } from "node:fs";
|
|
4509
|
+
import { dirname as dirname8 } from "node:path";
|
|
4510
|
+
function getInstallDecisionsPath() {
|
|
4511
|
+
return lspRequestContext().installDecisionsPath;
|
|
4512
|
+
}
|
|
4513
|
+
function loadInstallDecisions() {
|
|
4514
|
+
const path = getInstallDecisionsPath();
|
|
4515
|
+
if (!existsSync8(path))
|
|
4516
|
+
return {};
|
|
4517
|
+
try {
|
|
4518
|
+
const parsed = JSON.parse(readFileSync4(path, "utf8"));
|
|
4519
|
+
return isInstallDecisions(parsed) ? parsed : {};
|
|
4520
|
+
} catch {
|
|
4521
|
+
return {};
|
|
4522
|
+
}
|
|
4523
|
+
}
|
|
4524
|
+
function loadInstallDecision(serverId) {
|
|
4525
|
+
return loadInstallDecisions()[serverId];
|
|
4526
|
+
}
|
|
4527
|
+
function recordInstallDecision(serverId, decision, decidedAt = new Date().toISOString()) {
|
|
4528
|
+
const decisions = loadInstallDecisions();
|
|
4529
|
+
decisions[serverId] = { decision, decidedAt };
|
|
4530
|
+
writeInstallDecisions(decisions);
|
|
4531
|
+
}
|
|
4532
|
+
function isInstallDecision(value) {
|
|
4533
|
+
return value === "declined" || value === "allowed";
|
|
4534
|
+
}
|
|
4535
|
+
function writeInstallDecisions(decisions) {
|
|
4536
|
+
const path = getInstallDecisionsPath();
|
|
4537
|
+
mkdirSync3(dirname8(path), { recursive: true });
|
|
4538
|
+
const tmpPath = `${path}.tmp`;
|
|
4539
|
+
writeFileSync2(tmpPath, `${JSON.stringify(decisions, null, 2)}
|
|
4540
|
+
`, "utf8");
|
|
4541
|
+
renameSync2(tmpPath, path);
|
|
4542
|
+
}
|
|
4543
|
+
function isInstallDecisions(value) {
|
|
4544
|
+
return isRecord5(value) && Object.values(value).every(isInstallDecisionRecord);
|
|
4545
|
+
}
|
|
4546
|
+
function isInstallDecisionRecord(value) {
|
|
4547
|
+
if (!isRecord5(value))
|
|
4548
|
+
return false;
|
|
4549
|
+
return isInstallDecision(value["decision"]) && typeof value["decidedAt"] === "string";
|
|
4550
|
+
}
|
|
4551
|
+
function isRecord5(value) {
|
|
4552
|
+
return typeof value === "object" && value !== null && !Array.isArray(value);
|
|
4553
|
+
}
|
|
4554
|
+
|
|
4357
4555
|
// ../lsp-core/src/lsp/config-loader.ts
|
|
4556
|
+
import { existsSync as existsSync9, readFileSync as readFileSync5 } from "node:fs";
|
|
4358
4557
|
function getProjectConfigPaths() {
|
|
4359
4558
|
return lspRequestContext().projectConfigPaths;
|
|
4360
4559
|
}
|
|
4361
4560
|
function getUserConfigPath() {
|
|
4362
4561
|
return lspRequestContext().userConfigPath;
|
|
4363
4562
|
}
|
|
4364
|
-
function loadJsonFile(
|
|
4365
|
-
if (!
|
|
4563
|
+
function loadJsonFile(path) {
|
|
4564
|
+
if (!existsSync9(path))
|
|
4366
4565
|
return null;
|
|
4367
4566
|
try {
|
|
4368
|
-
const parsed = JSON.parse(readFileSync5(
|
|
4567
|
+
const parsed = JSON.parse(readFileSync5(path, "utf-8"));
|
|
4369
4568
|
return isConfigJson(parsed) ? parsed : null;
|
|
4370
4569
|
} catch {
|
|
4371
4570
|
return null;
|
|
@@ -4382,8 +4581,8 @@ function loadAllConfigs() {
|
|
|
4382
4581
|
return configs;
|
|
4383
4582
|
}
|
|
4384
4583
|
function loadFirstJsonFile(paths) {
|
|
4385
|
-
for (const
|
|
4386
|
-
const config = loadJsonFile(
|
|
4584
|
+
for (const path of paths) {
|
|
4585
|
+
const config = loadJsonFile(path);
|
|
4387
4586
|
if (config)
|
|
4388
4587
|
return config;
|
|
4389
4588
|
}
|
|
@@ -4409,10 +4608,10 @@ function getMergedServers() {
|
|
|
4409
4608
|
}
|
|
4410
4609
|
if (seen.has(id))
|
|
4411
4610
|
continue;
|
|
4412
|
-
const
|
|
4413
|
-
if (!
|
|
4611
|
+
const server = createServerFromEntry(id, entry, source);
|
|
4612
|
+
if (!server)
|
|
4414
4613
|
continue;
|
|
4415
|
-
servers.push(
|
|
4614
|
+
servers.push(server);
|
|
4416
4615
|
seen.add(id);
|
|
4417
4616
|
}
|
|
4418
4617
|
}
|
|
@@ -4444,7 +4643,7 @@ function createServerFromEntry(id, entry, source) {
|
|
|
4444
4643
|
if (source === "project") {
|
|
4445
4644
|
if (!builtin)
|
|
4446
4645
|
return null;
|
|
4447
|
-
const
|
|
4646
|
+
const server = createServer({
|
|
4448
4647
|
id,
|
|
4449
4648
|
command: builtin.command,
|
|
4450
4649
|
extensions: entry.extensions ?? builtin.extensions,
|
|
@@ -4452,35 +4651,35 @@ function createServerFromEntry(id, entry, source) {
|
|
|
4452
4651
|
source
|
|
4453
4652
|
});
|
|
4454
4653
|
if (entry.initialization !== undefined) {
|
|
4455
|
-
|
|
4654
|
+
server.initialization = entry.initialization;
|
|
4456
4655
|
}
|
|
4457
|
-
return
|
|
4656
|
+
return server;
|
|
4458
4657
|
}
|
|
4459
4658
|
if (entry.command && entry.extensions) {
|
|
4460
|
-
const
|
|
4659
|
+
const server = createServer({
|
|
4461
4660
|
id,
|
|
4462
4661
|
command: entry.command,
|
|
4463
4662
|
extensions: entry.extensions,
|
|
4464
4663
|
priority: entry.priority ?? 0,
|
|
4465
4664
|
source
|
|
4466
4665
|
});
|
|
4467
|
-
applyOptionalServerFields(
|
|
4468
|
-
return
|
|
4666
|
+
applyOptionalServerFields(server, entry);
|
|
4667
|
+
return server;
|
|
4469
4668
|
}
|
|
4470
4669
|
if (!builtin)
|
|
4471
4670
|
return null;
|
|
4472
|
-
const
|
|
4671
|
+
const server = createServer({
|
|
4473
4672
|
id,
|
|
4474
4673
|
command: entry.command ?? builtin.command,
|
|
4475
4674
|
extensions: entry.extensions ?? builtin.extensions,
|
|
4476
4675
|
priority: entry.priority ?? 0,
|
|
4477
4676
|
source
|
|
4478
4677
|
});
|
|
4479
|
-
applyOptionalServerFields(
|
|
4480
|
-
return
|
|
4678
|
+
applyOptionalServerFields(server, entry);
|
|
4679
|
+
return server;
|
|
4481
4680
|
}
|
|
4482
4681
|
function createServer(input) {
|
|
4483
|
-
const
|
|
4682
|
+
const server = {
|
|
4484
4683
|
id: input.id,
|
|
4485
4684
|
command: input.command,
|
|
4486
4685
|
extensions: input.extensions,
|
|
@@ -4488,19 +4687,19 @@ function createServer(input) {
|
|
|
4488
4687
|
source: input.source
|
|
4489
4688
|
};
|
|
4490
4689
|
if (input.env !== undefined) {
|
|
4491
|
-
|
|
4690
|
+
server.env = input.env;
|
|
4492
4691
|
}
|
|
4493
4692
|
if (input.initialization !== undefined) {
|
|
4494
|
-
|
|
4693
|
+
server.initialization = input.initialization;
|
|
4495
4694
|
}
|
|
4496
|
-
return
|
|
4695
|
+
return server;
|
|
4497
4696
|
}
|
|
4498
|
-
function applyOptionalServerFields(
|
|
4697
|
+
function applyOptionalServerFields(server, entry) {
|
|
4499
4698
|
if (entry.env !== undefined) {
|
|
4500
|
-
|
|
4699
|
+
server.env = entry.env;
|
|
4501
4700
|
}
|
|
4502
4701
|
if (entry.initialization !== undefined) {
|
|
4503
|
-
|
|
4702
|
+
server.initialization = entry.initialization;
|
|
4504
4703
|
}
|
|
4505
4704
|
}
|
|
4506
4705
|
function isConfigJson(value) {
|
|
@@ -4550,64 +4749,165 @@ function getDisabledServerIds() {
|
|
|
4550
4749
|
}
|
|
4551
4750
|
|
|
4552
4751
|
// ../lsp-core/src/lsp/server-installation.ts
|
|
4553
|
-
import { existsSync as
|
|
4554
|
-
import { delimiter as delimiter3, join as
|
|
4555
|
-
|
|
4556
|
-
|
|
4557
|
-
|
|
4558
|
-
|
|
4559
|
-
|
|
4560
|
-
|
|
4561
|
-
|
|
4562
|
-
|
|
4563
|
-
|
|
4752
|
+
import { existsSync as existsSync10 } from "node:fs";
|
|
4753
|
+
import { delimiter as delimiter3, dirname as dirname9, isAbsolute as isAbsolute5, join as join4, resolve as resolve7 } from "node:path";
|
|
4754
|
+
var LOCAL_BIN_RULES = [
|
|
4755
|
+
{
|
|
4756
|
+
markers: ["package.json", "bun.lock", "bun.lockb", "package-lock.json", "yarn.lock", "pnpm-lock.yaml"],
|
|
4757
|
+
binDirs: [join4("node_modules", ".bin")]
|
|
4758
|
+
},
|
|
4759
|
+
{
|
|
4760
|
+
markers: [
|
|
4761
|
+
"pyproject.toml",
|
|
4762
|
+
"ty.toml",
|
|
4763
|
+
"requirements.txt",
|
|
4764
|
+
"setup.py",
|
|
4765
|
+
"setup.cfg",
|
|
4766
|
+
"Pipfile",
|
|
4767
|
+
"pyrightconfig.json",
|
|
4768
|
+
"ruff.toml",
|
|
4769
|
+
".ruff.toml"
|
|
4770
|
+
],
|
|
4771
|
+
binDirs: [
|
|
4772
|
+
join4(".venv", "bin"),
|
|
4773
|
+
join4(".venv", "Scripts"),
|
|
4774
|
+
join4("venv", "bin"),
|
|
4775
|
+
join4("venv", "Scripts"),
|
|
4776
|
+
join4(".env", "bin"),
|
|
4777
|
+
join4(".env", "Scripts")
|
|
4778
|
+
]
|
|
4779
|
+
},
|
|
4780
|
+
{
|
|
4781
|
+
markers: ["Gemfile", "Gemfile.lock"],
|
|
4782
|
+
binDirs: [join4("vendor", "bundle", "bin"), "bin"]
|
|
4783
|
+
},
|
|
4784
|
+
{
|
|
4785
|
+
markers: ["go.mod", "go.sum", "go.work"],
|
|
4786
|
+
binDirs: ["bin"]
|
|
4564
4787
|
}
|
|
4565
|
-
|
|
4566
|
-
|
|
4567
|
-
|
|
4568
|
-
|
|
4569
|
-
|
|
4570
|
-
|
|
4571
|
-
|
|
4572
|
-
|
|
4573
|
-
|
|
4788
|
+
];
|
|
4789
|
+
var resolutionCache = new Map;
|
|
4790
|
+
var probeCount = 0;
|
|
4791
|
+
function probe(path) {
|
|
4792
|
+
probeCount += 1;
|
|
4793
|
+
return existsSync10(path);
|
|
4794
|
+
}
|
|
4795
|
+
function executableSuffixes(platform, pathExt) {
|
|
4796
|
+
if (platform !== "win32")
|
|
4797
|
+
return [""];
|
|
4798
|
+
const configured = pathExt ?? process.env["PATHEXT"] ?? "";
|
|
4799
|
+
const systemExts = configured.split(";").filter((entry) => entry.length > 0).map((entry) => entry.toLowerCase());
|
|
4800
|
+
return [...new Set(["", ...systemExts, ".exe", ".cmd", ".bat", ".ps1"])];
|
|
4801
|
+
}
|
|
4802
|
+
function probeWithSuffixes(directory, command, suffixes) {
|
|
4803
|
+
for (const suffix of suffixes) {
|
|
4804
|
+
const candidate = join4(directory, command + suffix);
|
|
4805
|
+
if (probe(candidate))
|
|
4806
|
+
return candidate;
|
|
4807
|
+
}
|
|
4808
|
+
return null;
|
|
4809
|
+
}
|
|
4810
|
+
function resolveLocal(command, workingDirectory, suffixes, stopAt) {
|
|
4811
|
+
const boundary = stopAt === undefined ? undefined : resolve7(stopAt);
|
|
4812
|
+
let current = resolve7(workingDirectory);
|
|
4813
|
+
while (true) {
|
|
4814
|
+
for (const rule of LOCAL_BIN_RULES) {
|
|
4815
|
+
if (!rule.markers.some((marker) => probe(join4(current, marker))))
|
|
4816
|
+
continue;
|
|
4817
|
+
for (const binDir of rule.binDirs) {
|
|
4818
|
+
const found = probeWithSuffixes(join4(current, binDir), command, suffixes);
|
|
4819
|
+
if (found !== null)
|
|
4820
|
+
return found;
|
|
4821
|
+
}
|
|
4574
4822
|
}
|
|
4823
|
+
if (probe(join4(current, ".git")))
|
|
4824
|
+
return null;
|
|
4825
|
+
if (boundary !== undefined && current === boundary)
|
|
4826
|
+
return null;
|
|
4827
|
+
const parent = dirname9(current);
|
|
4828
|
+
if (parent === current)
|
|
4829
|
+
return null;
|
|
4830
|
+
current = parent;
|
|
4575
4831
|
}
|
|
4576
|
-
|
|
4577
|
-
|
|
4832
|
+
}
|
|
4833
|
+
function resolveFromPath(command, suffixes, platform, pathEnvOverride) {
|
|
4834
|
+
let pathEnv = pathEnvOverride ?? process.env["PATH"] ?? "";
|
|
4835
|
+
if (platform === "win32" && !pathEnv) {
|
|
4578
4836
|
pathEnv = process.env["Path"] ?? "";
|
|
4579
4837
|
}
|
|
4580
|
-
const
|
|
4581
|
-
|
|
4582
|
-
|
|
4583
|
-
|
|
4584
|
-
|
|
4585
|
-
|
|
4586
|
-
}
|
|
4838
|
+
for (const entry of pathEnv.split(delimiter3)) {
|
|
4839
|
+
if (entry.length === 0)
|
|
4840
|
+
continue;
|
|
4841
|
+
const found = probeWithSuffixes(entry, command, suffixes);
|
|
4842
|
+
if (found !== null)
|
|
4843
|
+
return found;
|
|
4587
4844
|
}
|
|
4588
|
-
|
|
4589
|
-
|
|
4590
|
-
|
|
4845
|
+
return null;
|
|
4846
|
+
}
|
|
4847
|
+
function resolveServerBinary(command, workingDirectory, options = {}) {
|
|
4848
|
+
if (command.length === 0)
|
|
4849
|
+
return null;
|
|
4850
|
+
const [cmd] = command;
|
|
4851
|
+
if (cmd === undefined || cmd.length === 0)
|
|
4852
|
+
return null;
|
|
4853
|
+
const platform = options.platform ?? process.platform;
|
|
4854
|
+
const suffixes = executableSuffixes(platform, options.pathExt);
|
|
4855
|
+
if (cmd.includes("/") || cmd.includes("\\")) {
|
|
4856
|
+
const explicit = isAbsolute5(cmd) ? cmd : resolve7(workingDirectory ?? process.cwd(), cmd);
|
|
4857
|
+
return probe(explicit) ? explicit : null;
|
|
4858
|
+
}
|
|
4859
|
+
const cacheKey = JSON.stringify([
|
|
4860
|
+
workingDirectory ?? "",
|
|
4861
|
+
cmd,
|
|
4862
|
+
platform,
|
|
4863
|
+
options.stopAt ?? "",
|
|
4864
|
+
options.pathExt ?? "",
|
|
4865
|
+
options.pathEnv ?? process.env["PATH"] ?? ""
|
|
4866
|
+
]);
|
|
4867
|
+
const cached = resolutionCache.get(cacheKey);
|
|
4868
|
+
if (cached !== undefined)
|
|
4869
|
+
return cached;
|
|
4870
|
+
let resolved = null;
|
|
4871
|
+
if (workingDirectory !== undefined && workingDirectory.length > 0) {
|
|
4872
|
+
resolved = resolveLocal(cmd, workingDirectory, suffixes, options.stopAt);
|
|
4873
|
+
}
|
|
4874
|
+
resolved ??= resolveFromPath(cmd, suffixes, platform, options.pathEnv);
|
|
4875
|
+
if (resolved === null && cmd === "node")
|
|
4876
|
+
resolved = cmd;
|
|
4877
|
+
resolutionCache.set(cacheKey, resolved);
|
|
4878
|
+
return resolved;
|
|
4879
|
+
}
|
|
4880
|
+
function isServerInstalled(command, workingDirectory, options = {}) {
|
|
4881
|
+
if (command.length === 0)
|
|
4882
|
+
return false;
|
|
4883
|
+
return resolveServerBinary(command, workingDirectory, options) !== null;
|
|
4591
4884
|
}
|
|
4592
4885
|
|
|
4593
4886
|
// ../lsp-core/src/lsp/server-resolution.ts
|
|
4887
|
+
function withResolvedCommand(command, binaryPath) {
|
|
4888
|
+
return [binaryPath, ...command.slice(1)];
|
|
4889
|
+
}
|
|
4594
4890
|
function findServerForExtension(ext) {
|
|
4595
4891
|
const servers = getMergedServers();
|
|
4596
|
-
|
|
4597
|
-
|
|
4892
|
+
const workingDirectory = contextCwd();
|
|
4893
|
+
for (const server of servers) {
|
|
4894
|
+
if (!server.extensions.includes(ext))
|
|
4895
|
+
continue;
|
|
4896
|
+
const binaryPath = resolveServerBinary(server.command, workingDirectory);
|
|
4897
|
+
if (binaryPath !== null) {
|
|
4598
4898
|
const resolvedServer = {
|
|
4599
|
-
id:
|
|
4600
|
-
command:
|
|
4601
|
-
extensions:
|
|
4602
|
-
priority:
|
|
4899
|
+
id: server.id,
|
|
4900
|
+
command: withResolvedCommand(server.command, binaryPath),
|
|
4901
|
+
extensions: server.extensions,
|
|
4902
|
+
priority: server.priority
|
|
4603
4903
|
};
|
|
4604
|
-
if (
|
|
4904
|
+
if (server.env !== undefined) {
|
|
4605
4905
|
return {
|
|
4606
4906
|
status: "found",
|
|
4607
4907
|
server: {
|
|
4608
4908
|
...resolvedServer,
|
|
4609
|
-
env:
|
|
4610
|
-
...
|
|
4909
|
+
env: server.env,
|
|
4910
|
+
...server.initialization === undefined ? {} : { initialization: server.initialization }
|
|
4611
4911
|
}
|
|
4612
4912
|
};
|
|
4613
4913
|
}
|
|
@@ -4615,20 +4915,20 @@ function findServerForExtension(ext) {
|
|
|
4615
4915
|
status: "found",
|
|
4616
4916
|
server: {
|
|
4617
4917
|
...resolvedServer,
|
|
4618
|
-
...
|
|
4918
|
+
...server.initialization === undefined ? {} : { initialization: server.initialization }
|
|
4619
4919
|
}
|
|
4620
4920
|
};
|
|
4621
4921
|
}
|
|
4622
4922
|
}
|
|
4623
|
-
for (const
|
|
4624
|
-
if (
|
|
4625
|
-
const installHint = LSP_INSTALL_HINTS[
|
|
4923
|
+
for (const server of servers) {
|
|
4924
|
+
if (server.extensions.includes(ext)) {
|
|
4925
|
+
const installHint = LSP_INSTALL_HINTS[server.id] ?? `Install '${server.command[0]}' and ensure it's in your PATH`;
|
|
4626
4926
|
return {
|
|
4627
4927
|
status: "not_installed",
|
|
4628
4928
|
server: {
|
|
4629
|
-
id:
|
|
4630
|
-
command:
|
|
4631
|
-
extensions:
|
|
4929
|
+
id: server.id,
|
|
4930
|
+
command: server.command,
|
|
4931
|
+
extensions: server.extensions
|
|
4632
4932
|
},
|
|
4633
4933
|
installHint
|
|
4634
4934
|
};
|
|
@@ -4644,20 +4944,21 @@ function findServerForExtension(ext) {
|
|
|
4644
4944
|
function getAllServers() {
|
|
4645
4945
|
const servers = getMergedServers();
|
|
4646
4946
|
const disabled = getDisabledServerIds();
|
|
4947
|
+
const workingDirectory = contextCwd();
|
|
4647
4948
|
const result = [];
|
|
4648
4949
|
const seen = new Set;
|
|
4649
|
-
for (const
|
|
4650
|
-
if (seen.has(
|
|
4950
|
+
for (const server of servers) {
|
|
4951
|
+
if (seen.has(server.id))
|
|
4651
4952
|
continue;
|
|
4652
4953
|
result.push({
|
|
4653
|
-
id:
|
|
4654
|
-
installed: isServerInstalled(
|
|
4655
|
-
extensions:
|
|
4954
|
+
id: server.id,
|
|
4955
|
+
installed: isServerInstalled(server.command, workingDirectory),
|
|
4956
|
+
extensions: server.extensions,
|
|
4656
4957
|
disabled: false,
|
|
4657
|
-
source:
|
|
4658
|
-
priority:
|
|
4958
|
+
source: server.source,
|
|
4959
|
+
priority: server.priority
|
|
4659
4960
|
});
|
|
4660
|
-
seen.add(
|
|
4961
|
+
seen.add(server.id);
|
|
4661
4962
|
}
|
|
4662
4963
|
for (const id of disabled) {
|
|
4663
4964
|
if (seen.has(id))
|
|
@@ -4665,7 +4966,7 @@ function getAllServers() {
|
|
|
4665
4966
|
const builtin = BUILTIN_SERVERS[id];
|
|
4666
4967
|
result.push({
|
|
4667
4968
|
id,
|
|
4668
|
-
installed: builtin ? isServerInstalled(builtin.command) : false,
|
|
4969
|
+
installed: builtin ? isServerInstalled(builtin.command, workingDirectory) : false,
|
|
4669
4970
|
extensions: builtin?.extensions ?? [],
|
|
4670
4971
|
disabled: true,
|
|
4671
4972
|
source: "disabled",
|
|
@@ -4676,7 +4977,6 @@ function getAllServers() {
|
|
|
4676
4977
|
}
|
|
4677
4978
|
|
|
4678
4979
|
// ../lsp-core/src/lsp/client-wrapper.ts
|
|
4679
|
-
var WORKSPACE_MARKERS = [".git", "package.json", "pyproject.toml", "Cargo.toml", "go.mod", "pom.xml", "build.gradle"];
|
|
4680
4980
|
function isDirectoryPath(filePath) {
|
|
4681
4981
|
try {
|
|
4682
4982
|
return statSync4(filePath).isDirectory();
|
|
@@ -4689,36 +4989,40 @@ function findWorkspaceRoot(filePath) {
|
|
|
4689
4989
|
const abs = resolveReadablePathInsideContext(filePath);
|
|
4690
4990
|
let dir = abs;
|
|
4691
4991
|
if (!isDirectoryPath(dir)) {
|
|
4692
|
-
dir =
|
|
4992
|
+
dir = dirname10(dir);
|
|
4693
4993
|
}
|
|
4994
|
+
if (!isPathInside(cwd, abs))
|
|
4995
|
+
return findWorkspaceRootOutsideContext(dir);
|
|
4694
4996
|
const fallbackRoot = nearestExistingDirectoryInsideContext(dir, cwd) ?? cwd;
|
|
4997
|
+
let nearestPackageRoot;
|
|
4695
4998
|
while (isPathInside(cwd, dir)) {
|
|
4696
4999
|
const canonicalDir = existingDirectoryInsideContext(dir, cwd);
|
|
4697
5000
|
if (canonicalDir !== undefined) {
|
|
4698
|
-
|
|
4699
|
-
|
|
4700
|
-
|
|
4701
|
-
|
|
5001
|
+
if (existsSync11(join5(dir, GIT_WORKSPACE_MARKER))) {
|
|
5002
|
+
return canonicalDir;
|
|
5003
|
+
}
|
|
5004
|
+
if (nearestPackageRoot === undefined && hasProjectWorkspaceMarker(dir)) {
|
|
5005
|
+
nearestPackageRoot = canonicalDir;
|
|
4702
5006
|
}
|
|
4703
5007
|
}
|
|
4704
5008
|
if (dir === cwd)
|
|
4705
5009
|
break;
|
|
4706
|
-
dir =
|
|
5010
|
+
dir = dirname10(dir);
|
|
4707
5011
|
}
|
|
4708
|
-
return fallbackRoot;
|
|
5012
|
+
return nearestPackageRoot ?? fallbackRoot;
|
|
5013
|
+
}
|
|
5014
|
+
function hasProjectWorkspaceMarker(directory) {
|
|
5015
|
+
return PROJECT_WORKSPACE_MARKERS.some((marker) => existsSync11(join5(directory, marker)));
|
|
4709
5016
|
}
|
|
4710
5017
|
function resolveReadablePathInsideContext(filePath) {
|
|
4711
5018
|
const cwd = contextCwd();
|
|
4712
|
-
const abs =
|
|
5019
|
+
const abs = resolve8(cwd, filePath);
|
|
4713
5020
|
if (isPathInside(cwd, abs))
|
|
4714
5021
|
return abs;
|
|
4715
5022
|
const rebased = rebaseThroughCanonicalAncestor(abs, cwd);
|
|
4716
5023
|
if (rebased !== undefined)
|
|
4717
5024
|
return rebased;
|
|
4718
|
-
|
|
4719
|
-
if (isPathInside(cwd, canonical))
|
|
4720
|
-
return canonical;
|
|
4721
|
-
throw new LspInvalidPathError(`LSP file path must be inside request cwd: ${filePath}`);
|
|
5025
|
+
return canonicalizeExistingOrNearestAncestor(abs);
|
|
4722
5026
|
}
|
|
4723
5027
|
function resolvePathInsideContext(filePath) {
|
|
4724
5028
|
const cwd = contextCwd();
|
|
@@ -4729,16 +5033,16 @@ function resolvePathInsideContext(filePath) {
|
|
|
4729
5033
|
}
|
|
4730
5034
|
return canonical;
|
|
4731
5035
|
}
|
|
4732
|
-
function rebaseThroughCanonicalAncestor(
|
|
4733
|
-
let current =
|
|
5036
|
+
function rebaseThroughCanonicalAncestor(path, cwd) {
|
|
5037
|
+
let current = path;
|
|
4734
5038
|
const suffix = [];
|
|
4735
5039
|
while (true) {
|
|
4736
|
-
if (
|
|
4737
|
-
const canonical =
|
|
5040
|
+
if (existsSync11(current)) {
|
|
5041
|
+
const canonical = realpathSync5(current);
|
|
4738
5042
|
if (isPathInside(cwd, canonical))
|
|
4739
|
-
return suffix.length === 0 ? canonical :
|
|
5043
|
+
return suffix.length === 0 ? canonical : join5(canonical, ...suffix);
|
|
4740
5044
|
}
|
|
4741
|
-
const parent =
|
|
5045
|
+
const parent = dirname10(current);
|
|
4742
5046
|
if (parent === current)
|
|
4743
5047
|
return;
|
|
4744
5048
|
suffix.unshift(basename3(current));
|
|
@@ -4746,9 +5050,9 @@ function rebaseThroughCanonicalAncestor(path2, cwd) {
|
|
|
4746
5050
|
}
|
|
4747
5051
|
}
|
|
4748
5052
|
function existingDirectoryInsideContext(directory, cwd) {
|
|
4749
|
-
if (!
|
|
5053
|
+
if (!existsSync11(directory))
|
|
4750
5054
|
return;
|
|
4751
|
-
const canonical =
|
|
5055
|
+
const canonical = realpathSync5(directory);
|
|
4752
5056
|
if (!statSync4(canonical).isDirectory())
|
|
4753
5057
|
return;
|
|
4754
5058
|
return isPathInside(cwd, canonical) ? canonical : undefined;
|
|
@@ -4761,7 +5065,7 @@ function nearestExistingDirectoryInsideContext(directory, cwd) {
|
|
|
4761
5065
|
return canonical;
|
|
4762
5066
|
if (current === cwd)
|
|
4763
5067
|
return;
|
|
4764
|
-
current =
|
|
5068
|
+
current = dirname10(current);
|
|
4765
5069
|
}
|
|
4766
5070
|
return;
|
|
4767
5071
|
}
|
|
@@ -4788,33 +5092,46 @@ function formatServerLookupError(result) {
|
|
|
4788
5092
|
].join(`
|
|
4789
5093
|
`);
|
|
4790
5094
|
}
|
|
5095
|
+
function formatInstallOptions(serverId, installHint) {
|
|
5096
|
+
const localHint = LSP_LOCAL_INSTALL_HINTS[serverId];
|
|
5097
|
+
if (localHint === undefined) {
|
|
5098
|
+
return ["To install, run:", ` ${installHint}`];
|
|
5099
|
+
}
|
|
5100
|
+
return [
|
|
5101
|
+
"To install in THIS repository (preferred — no global install needed):",
|
|
5102
|
+
` ${localHint}`,
|
|
5103
|
+
"",
|
|
5104
|
+
"Or install it globally:",
|
|
5105
|
+
` ${installHint}`
|
|
5106
|
+
];
|
|
5107
|
+
}
|
|
4791
5108
|
function formatNotInstalled(result) {
|
|
4792
|
-
const { server
|
|
4793
|
-
const extensions =
|
|
4794
|
-
const decision = loadInstallDecision(
|
|
5109
|
+
const { server, installHint } = result;
|
|
5110
|
+
const extensions = server.extensions.join(", ");
|
|
5111
|
+
const decision = loadInstallDecision(server.id)?.decision;
|
|
4795
5112
|
const context = lspRequestContext();
|
|
4796
5113
|
if (decision === "declined") {
|
|
4797
|
-
return `LSP server '${
|
|
5114
|
+
return `LSP server '${server.id}' (${extensions}) is NOT INSTALLED; user previously declined installation — proceed without LSP.`;
|
|
4798
5115
|
}
|
|
4799
5116
|
const header = [
|
|
4800
|
-
`LSP server '${
|
|
5117
|
+
`LSP server '${server.id}' for ${extensions} is NOT INSTALLED.`,
|
|
4801
5118
|
"",
|
|
4802
|
-
`Command not found: ${
|
|
5119
|
+
`Command not found: ${server.command[0]}`,
|
|
4803
5120
|
""
|
|
4804
5121
|
];
|
|
5122
|
+
const installOptions = formatInstallOptions(server.id, installHint);
|
|
4805
5123
|
if (decision === "allowed") {
|
|
4806
5124
|
return [
|
|
4807
5125
|
...header,
|
|
4808
5126
|
"The user has pre-authorized LSP installation. Run the install command, then retry this tool:",
|
|
4809
|
-
|
|
5127
|
+
...installOptions.slice(1)
|
|
4810
5128
|
].join(`
|
|
4811
5129
|
`);
|
|
4812
5130
|
}
|
|
4813
5131
|
if (!context.capabilities.installDecisionTool) {
|
|
4814
5132
|
return [
|
|
4815
5133
|
...header,
|
|
4816
|
-
|
|
4817
|
-
` ${installHint}`,
|
|
5134
|
+
...installOptions,
|
|
4818
5135
|
"",
|
|
4819
5136
|
"ACTION REQUIRED — ASK THE USER whether to install this LSP server.",
|
|
4820
5137
|
"Install-decision recording is unavailable in this harness; proceed without LSP if the user declines."
|
|
@@ -4823,13 +5140,12 @@ function formatNotInstalled(result) {
|
|
|
4823
5140
|
}
|
|
4824
5141
|
return [
|
|
4825
5142
|
...header,
|
|
4826
|
-
|
|
4827
|
-
` ${installHint}`,
|
|
5143
|
+
...installOptions,
|
|
4828
5144
|
"",
|
|
4829
5145
|
"ACTION REQUIRED — ASK THE USER whether to install this LSP server.",
|
|
4830
5146
|
"- If the user agrees: run the install command above, then retry this tool.",
|
|
4831
5147
|
"- If the user declines, OR has NOT explicitly asked for LSP installation:",
|
|
4832
|
-
` call lsp_install_decision { server_id: "${
|
|
5148
|
+
` call lsp_install_decision { server_id: "${server.id}", decision: "declined" },`,
|
|
4833
5149
|
` which writes to ${context.installDecisionsPath},`,
|
|
4834
5150
|
" then ignore this message and proceed WITHOUT LSP."
|
|
4835
5151
|
].join(`
|
|
@@ -4853,34 +5169,34 @@ async function withLspClient(filePath, fn, toolName, options = {}) {
|
|
|
4853
5169
|
if (result.status !== "found") {
|
|
4854
5170
|
throw new LspServerLookupError(formatServerLookupError(result), result);
|
|
4855
5171
|
}
|
|
4856
|
-
const
|
|
5172
|
+
const server = result.server;
|
|
4857
5173
|
const root = findWorkspaceRoot(absPath);
|
|
4858
5174
|
const manager = options.manager ?? getLspManager();
|
|
4859
5175
|
const acquireAndCall = async (allowRetry) => {
|
|
4860
|
-
const client = await manager.getClient(root,
|
|
5176
|
+
const client = await manager.getClient(root, server, options.signal);
|
|
4861
5177
|
try {
|
|
4862
5178
|
return await fn(client, root, absPath);
|
|
4863
5179
|
} catch (err) {
|
|
4864
5180
|
if (allowRetry && READ_ONLY_TOOLS.has(toolName) && isLspDeadConnectionError(err)) {
|
|
4865
|
-
manager.invalidateClient(root,
|
|
5181
|
+
manager.invalidateClient(root, server.id, client);
|
|
4866
5182
|
return acquireAndCall(false);
|
|
4867
5183
|
}
|
|
4868
5184
|
if (err instanceof LspRequestTimeoutError) {
|
|
4869
|
-
if (manager.isServerInitializing(root,
|
|
5185
|
+
if (manager.isServerInitializing(root, server.id)) {
|
|
4870
5186
|
throw new LspServerInitializingError(err);
|
|
4871
5187
|
}
|
|
4872
5188
|
}
|
|
4873
5189
|
throw err;
|
|
4874
5190
|
} finally {
|
|
4875
|
-
manager.releaseClient(root,
|
|
5191
|
+
manager.releaseClient(root, server.id);
|
|
4876
5192
|
}
|
|
4877
5193
|
};
|
|
4878
5194
|
return acquireAndCall(true);
|
|
4879
5195
|
}
|
|
4880
5196
|
|
|
4881
5197
|
// ../lsp-core/src/lsp/directory-diagnostics.ts
|
|
4882
|
-
import { existsSync as
|
|
4883
|
-
import { join as
|
|
5198
|
+
import { existsSync as existsSync12, lstatSync as lstatSync5, readdirSync as readdirSync3 } from "node:fs";
|
|
5199
|
+
import { join as join6, resolve as resolve9 } from "node:path";
|
|
4884
5200
|
|
|
4885
5201
|
// ../lsp-core/src/lsp/formatters.ts
|
|
4886
5202
|
import { fileURLToPath as fileURLToPath3 } from "node:url";
|
|
@@ -4895,10 +5211,10 @@ function uriToPath(uri) {
|
|
|
4895
5211
|
}
|
|
4896
5212
|
function formatLocation(loc) {
|
|
4897
5213
|
if ("targetUri" in loc) {
|
|
4898
|
-
const
|
|
4899
|
-
const
|
|
4900
|
-
const
|
|
4901
|
-
return `${
|
|
5214
|
+
const uri = uriToPath(loc.targetUri);
|
|
5215
|
+
const line = loc.targetRange.start.line + 1;
|
|
5216
|
+
const char = loc.targetRange.start.character;
|
|
5217
|
+
return `${uri}:${line}:${char}`;
|
|
4902
5218
|
}
|
|
4903
5219
|
const uri = uriToPath(loc.uri);
|
|
4904
5220
|
const line = loc.range.start.line + 1;
|
|
@@ -5010,7 +5326,7 @@ function collectFilesWithExtension(dir, extension, maxFiles) {
|
|
|
5010
5326
|
for (const entry of entries) {
|
|
5011
5327
|
if (files.length >= maxFiles)
|
|
5012
5328
|
return;
|
|
5013
|
-
const fullPath =
|
|
5329
|
+
const fullPath = join6(currentDir, entry);
|
|
5014
5330
|
let stat;
|
|
5015
5331
|
try {
|
|
5016
5332
|
stat = lstatSync5(fullPath);
|
|
@@ -5035,15 +5351,15 @@ async function aggregateDiagnosticsForDirectory(directory, extension, severity,
|
|
|
5035
5351
|
if (!extension.startsWith(".")) {
|
|
5036
5352
|
throw new LspInvalidPathError(`Extension must start with a dot (e.g., ".ts", not "${extension}"). Use ".${extension}" instead.`);
|
|
5037
5353
|
}
|
|
5038
|
-
const absDir =
|
|
5039
|
-
if (!
|
|
5354
|
+
const absDir = resolve9(options.workspaceRoot ?? contextCwd(), directory);
|
|
5355
|
+
if (!existsSync12(absDir)) {
|
|
5040
5356
|
throw new LspInvalidPathError(`Directory does not exist: ${absDir}`);
|
|
5041
5357
|
}
|
|
5042
5358
|
const serverResult = options.server === undefined ? findServerForExtension(extension) : { status: "found", server: options.server };
|
|
5043
5359
|
if (serverResult.status !== "found") {
|
|
5044
5360
|
throw new LspServerLookupError(formatServerLookupError(serverResult));
|
|
5045
5361
|
}
|
|
5046
|
-
const
|
|
5362
|
+
const server = serverResult.server;
|
|
5047
5363
|
const allFiles = (options.listFiles ?? collectFilesWithExtension)(absDir, extension, maxFiles + 1);
|
|
5048
5364
|
const wasCapped = allFiles.length > maxFiles;
|
|
5049
5365
|
const filesToProcess = allFiles.slice(0, maxFiles);
|
|
@@ -5063,7 +5379,7 @@ async function aggregateDiagnosticsForDirectory(directory, extension, severity,
|
|
|
5063
5379
|
const fileErrors = [];
|
|
5064
5380
|
const maxConcurrency = Math.max(1, options.maxConcurrency ?? DIRECTORY_DIAGNOSTICS_MAX_CONCURRENCY);
|
|
5065
5381
|
options.signal?.throwIfAborted();
|
|
5066
|
-
const client = await manager.getClient(root,
|
|
5382
|
+
const client = await manager.getClient(root, server, options.signal);
|
|
5067
5383
|
try {
|
|
5068
5384
|
let nextIndex = 0;
|
|
5069
5385
|
const workers = Array.from({ length: Math.min(maxConcurrency, filesToProcess.length) }, async () => {
|
|
@@ -5091,7 +5407,7 @@ async function aggregateDiagnosticsForDirectory(directory, extension, severity,
|
|
|
5091
5407
|
});
|
|
5092
5408
|
await Promise.all(workers);
|
|
5093
5409
|
} finally {
|
|
5094
|
-
manager.releaseClient(root,
|
|
5410
|
+
manager.releaseClient(root, server.id);
|
|
5095
5411
|
}
|
|
5096
5412
|
const displayDiagnostics = allDiagnostics.slice(0, DEFAULT_MAX_DIAGNOSTICS);
|
|
5097
5413
|
const wasDiagCapped = allDiagnostics.length > DEFAULT_MAX_DIAGNOSTICS;
|
|
@@ -5123,7 +5439,7 @@ async function aggregateDiagnosticsForDirectory(directory, extension, severity,
|
|
|
5123
5439
|
|
|
5124
5440
|
// ../lsp-core/src/lsp/infer-extension.ts
|
|
5125
5441
|
import { lstatSync as lstatSync6, readdirSync as readdirSync4 } from "node:fs";
|
|
5126
|
-
import { join as
|
|
5442
|
+
import { join as join7 } from "node:path";
|
|
5127
5443
|
var SKIP_DIRECTORIES2 = new Set(["node_modules", ".git", "dist", "build", ".next", "out"]);
|
|
5128
5444
|
var MAX_SCAN_ENTRIES = 500;
|
|
5129
5445
|
function inferExtensionFromDirectory(directory) {
|
|
@@ -5141,7 +5457,7 @@ function inferExtensionFromDirectory(directory) {
|
|
|
5141
5457
|
for (const entry of entries) {
|
|
5142
5458
|
if (scanned >= MAX_SCAN_ENTRIES)
|
|
5143
5459
|
return;
|
|
5144
|
-
const fullPath =
|
|
5460
|
+
const fullPath = join7(dir, entry);
|
|
5145
5461
|
let stat;
|
|
5146
5462
|
try {
|
|
5147
5463
|
stat = lstatSync6(fullPath);
|
|
@@ -5300,8 +5616,8 @@ function clientOptions(signal) {
|
|
|
5300
5616
|
}
|
|
5301
5617
|
|
|
5302
5618
|
// ../lsp-core/src/tools/result.ts
|
|
5303
|
-
function text(
|
|
5304
|
-
return { content: [{ type: "text", text
|
|
5619
|
+
function text(text, details, isError = false) {
|
|
5620
|
+
return { content: [{ type: "text", text }], details, isError };
|
|
5305
5621
|
}
|
|
5306
5622
|
|
|
5307
5623
|
// ../lsp-core/src/tools/diagnostics.ts
|
|
@@ -5321,7 +5637,7 @@ async function executeLspDiagnostics(params, signal) {
|
|
|
5321
5637
|
const extension = inferExtensionFromDirectory(absPath);
|
|
5322
5638
|
if (!extension) {
|
|
5323
5639
|
const message = `No supported source files found in directory: ${absPath}`;
|
|
5324
|
-
const
|
|
5640
|
+
const details = {
|
|
5325
5641
|
filePath,
|
|
5326
5642
|
severity,
|
|
5327
5643
|
mode: "directory",
|
|
@@ -5331,24 +5647,24 @@ async function executeLspDiagnostics(params, signal) {
|
|
|
5331
5647
|
error: message,
|
|
5332
5648
|
errorKind: "no_files"
|
|
5333
5649
|
};
|
|
5334
|
-
return text(message,
|
|
5650
|
+
return text(message, details);
|
|
5335
5651
|
}
|
|
5336
|
-
const
|
|
5337
|
-
const
|
|
5652
|
+
const output = await aggregateDiagnosticsForDirectory(absPath, extension, severity, undefined, signal === undefined ? {} : { signal });
|
|
5653
|
+
const details = {
|
|
5338
5654
|
filePath,
|
|
5339
5655
|
severity,
|
|
5340
5656
|
mode: "directory",
|
|
5341
5657
|
diagnostics: [],
|
|
5342
|
-
totalDiagnostics:
|
|
5658
|
+
totalDiagnostics: output.totalDiagnostics,
|
|
5343
5659
|
truncated: false,
|
|
5344
|
-
fileFailures: [...
|
|
5660
|
+
fileFailures: [...output.fileFailures]
|
|
5345
5661
|
};
|
|
5346
|
-
return text(
|
|
5662
|
+
return text(output.output, details);
|
|
5347
5663
|
}
|
|
5348
5664
|
const result = await withLspClient(filePath, async (client, _workspaceRoot, resolvedFilePath) => client.diagnostics(resolvedFilePath, signal), "diagnostics", clientOptions(signal));
|
|
5349
5665
|
if (result.transientError) {
|
|
5350
5666
|
const message = result.transientError.message;
|
|
5351
|
-
const
|
|
5667
|
+
const details = {
|
|
5352
5668
|
filePath,
|
|
5353
5669
|
severity,
|
|
5354
5670
|
mode: "file",
|
|
@@ -5358,7 +5674,7 @@ async function executeLspDiagnostics(params, signal) {
|
|
|
5358
5674
|
error: message,
|
|
5359
5675
|
errorKind: result.transientError.kind
|
|
5360
5676
|
};
|
|
5361
|
-
return text(message,
|
|
5677
|
+
return text(message, details, true);
|
|
5362
5678
|
}
|
|
5363
5679
|
const diagnostics = filterDiagnosticsBySeverity(asDiagnosticArray(result), severity);
|
|
5364
5680
|
const total = diagnostics.length;
|
|
@@ -5392,6 +5708,96 @@ async function executeLspDiagnostics(params, signal) {
|
|
|
5392
5708
|
throw error;
|
|
5393
5709
|
}
|
|
5394
5710
|
}
|
|
5711
|
+
// ../lsp-core/src/lsp/format-document.ts
|
|
5712
|
+
import { readFileSync as readFileSync6, renameSync as renameSync3, unlinkSync as unlinkSync2, writeFileSync as writeFileSync3 } from "node:fs";
|
|
5713
|
+
var DEFAULT_FORMATTING_OPTIONS = {
|
|
5714
|
+
tabSize: 4,
|
|
5715
|
+
insertSpaces: false,
|
|
5716
|
+
trimTrailingWhitespace: true,
|
|
5717
|
+
insertFinalNewline: true,
|
|
5718
|
+
trimFinalNewlines: true
|
|
5719
|
+
};
|
|
5720
|
+
var UNCHANGED = { status: "unchanged", linesAdded: 0, linesRemoved: 0 };
|
|
5721
|
+
async function formatDocumentWithClient(client, filePath, options = {}) {
|
|
5722
|
+
const edits = await client.formatDocument(filePath, options.formattingOptions ?? DEFAULT_FORMATTING_OPTIONS, options.signal);
|
|
5723
|
+
if (edits === null)
|
|
5724
|
+
return { status: "unavailable", reason: "capability_not_advertised" };
|
|
5725
|
+
if (edits.length === 0)
|
|
5726
|
+
return UNCHANGED;
|
|
5727
|
+
const before = readFileSync6(filePath, "utf-8");
|
|
5728
|
+
const normalized = normalizeTextEdits(before, edits, 0);
|
|
5729
|
+
if (normalized.text === before)
|
|
5730
|
+
return UNCHANGED;
|
|
5731
|
+
writeAtomically(filePath, normalized.text);
|
|
5732
|
+
await client.openFile(filePath);
|
|
5733
|
+
return {
|
|
5734
|
+
status: "formatted",
|
|
5735
|
+
...lineDelta(normalized.edits)
|
|
5736
|
+
};
|
|
5737
|
+
}
|
|
5738
|
+
function lineDelta(edits) {
|
|
5739
|
+
let linesAdded = 0;
|
|
5740
|
+
let linesRemoved = 0;
|
|
5741
|
+
for (const edit of edits) {
|
|
5742
|
+
linesRemoved += edit.range.end.line - edit.range.start.line + 1;
|
|
5743
|
+
linesAdded += edit.newText.split(`
|
|
5744
|
+
`).length;
|
|
5745
|
+
}
|
|
5746
|
+
return { linesAdded, linesRemoved };
|
|
5747
|
+
}
|
|
5748
|
+
function writeAtomically(filePath, content) {
|
|
5749
|
+
const tempPath = `${filePath}.omo-format.tmp`;
|
|
5750
|
+
writeFileSync3(tempPath, content, "utf-8");
|
|
5751
|
+
try {
|
|
5752
|
+
renameSync3(tempPath, filePath);
|
|
5753
|
+
} catch (error) {
|
|
5754
|
+
try {
|
|
5755
|
+
unlinkSync2(tempPath);
|
|
5756
|
+
} catch {}
|
|
5757
|
+
throw error;
|
|
5758
|
+
}
|
|
5759
|
+
}
|
|
5760
|
+
|
|
5761
|
+
// ../lsp-core/src/tools/format.ts
|
|
5762
|
+
async function executeLspFormat(params, signal) {
|
|
5763
|
+
const filePath = requireString(params, "filePath");
|
|
5764
|
+
try {
|
|
5765
|
+
const result = await withLspClient(filePath, async (client, _workspaceRoot, resolvedFilePath) => formatDocumentWithClient(client, resolvedFilePath, signal === undefined ? {} : { signal }), "format", clientOptions(signal));
|
|
5766
|
+
return text(describeResult(filePath, result), formatDetails(filePath, result));
|
|
5767
|
+
} catch (error) {
|
|
5768
|
+
const missingDependency = missingDependencyResult(error, {
|
|
5769
|
+
filePath,
|
|
5770
|
+
status: "unavailable",
|
|
5771
|
+
reason: "server_unavailable",
|
|
5772
|
+
linesAdded: 0,
|
|
5773
|
+
linesRemoved: 0
|
|
5774
|
+
});
|
|
5775
|
+
if (missingDependency)
|
|
5776
|
+
return missingDependency;
|
|
5777
|
+
throw error;
|
|
5778
|
+
}
|
|
5779
|
+
}
|
|
5780
|
+
function formatDetails(filePath, result) {
|
|
5781
|
+
if (result.status === "unavailable") {
|
|
5782
|
+
return { filePath, status: "unavailable", reason: result.reason, linesAdded: 0, linesRemoved: 0 };
|
|
5783
|
+
}
|
|
5784
|
+
return {
|
|
5785
|
+
filePath,
|
|
5786
|
+
status: result.status,
|
|
5787
|
+
linesAdded: result.linesAdded,
|
|
5788
|
+
linesRemoved: result.linesRemoved
|
|
5789
|
+
};
|
|
5790
|
+
}
|
|
5791
|
+
function describeResult(filePath, result) {
|
|
5792
|
+
if (result.status === "unavailable") {
|
|
5793
|
+
return `Formatting unavailable for ${filePath}: the language server does not advertise documentFormattingProvider.`;
|
|
5794
|
+
}
|
|
5795
|
+
if (result.status === "unchanged") {
|
|
5796
|
+
return `Already formatted: ${filePath}`;
|
|
5797
|
+
}
|
|
5798
|
+
return `Formatted ${filePath} (+${result.linesAdded}/-${result.linesRemoved} lines)`;
|
|
5799
|
+
}
|
|
5800
|
+
|
|
5395
5801
|
// ../lsp-core/src/tools/install-decision.ts
|
|
5396
5802
|
async function executeLspInstallDecision(params) {
|
|
5397
5803
|
const serverId = requireString(params, "server_id");
|
|
@@ -5399,7 +5805,7 @@ async function executeLspInstallDecision(params) {
|
|
|
5399
5805
|
if (!isInstallDecision(decision)) {
|
|
5400
5806
|
return text(`Invalid decision '${String(decision)}'. Expected "declined" or "allowed".`, { serverId, errorKind: "invalid_decision" }, true);
|
|
5401
5807
|
}
|
|
5402
|
-
const serverIds = [...new Set(getMergedServers().map((
|
|
5808
|
+
const serverIds = [...new Set(getMergedServers().map((server) => server.id))];
|
|
5403
5809
|
if (!serverIds.includes(serverId)) {
|
|
5404
5810
|
const preview = serverIds.slice(0, 20).join(", ");
|
|
5405
5811
|
return text(`Unknown LSP server '${serverId}'. Known servers: ${preview}${serverIds.length > 20 ? "..." : ""}`, { serverId, errorKind: "unknown_server" }, true);
|
|
@@ -5539,10 +5945,10 @@ function objectSchema(properties, required = []) {
|
|
|
5539
5945
|
async function executeLspStatus() {
|
|
5540
5946
|
const servers = getAllServers();
|
|
5541
5947
|
const snapshots = getLspManager().getSnapshot();
|
|
5542
|
-
const installed = servers.filter((
|
|
5543
|
-
const configuredLines = servers.map((
|
|
5544
|
-
const state =
|
|
5545
|
-
return `- ${
|
|
5948
|
+
const installed = servers.filter((server) => server.installed && !server.disabled);
|
|
5949
|
+
const configuredLines = servers.map((server) => {
|
|
5950
|
+
const state = server.disabled ? "disabled" : server.installed ? "installed" : "missing";
|
|
5951
|
+
return `- ${server.id}: ${state}; source=${server.source}; extensions=${server.extensions.join(", ")}`;
|
|
5546
5952
|
});
|
|
5547
5953
|
const activeLines = snapshots.map((snapshot) => {
|
|
5548
5954
|
const state = snapshot.alive ? snapshot.isInitializing ? "initializing" : "alive" : "dead";
|
|
@@ -5585,8 +5991,8 @@ async function executeLspSymbols(params, signal) {
|
|
|
5585
5991
|
errorKind: "missing_query"
|
|
5586
5992
|
});
|
|
5587
5993
|
}
|
|
5588
|
-
const
|
|
5589
|
-
return formatSymbolsResult(filePath, scope,
|
|
5994
|
+
const symbols = await withLspClient(filePath, async (client) => client.workspaceSymbols(query, signal), "workspaceSymbols", clientOptions(signal));
|
|
5995
|
+
return formatSymbolsResult(filePath, scope, symbols, limit, query);
|
|
5590
5996
|
}
|
|
5591
5997
|
const symbols = await withLspClient(filePath, async (client, _workspaceRoot, resolvedFilePath) => client.documentSymbols(resolvedFilePath, signal), "documentSymbols", clientOptions(signal));
|
|
5592
5998
|
return formatSymbolsResult(filePath, scope, symbols, limit);
|
|
@@ -5724,6 +6130,16 @@ var LSP_MCP_TOOLS = [
|
|
|
5724
6130
|
}, ["filePath", "line", "character", "newName"]),
|
|
5725
6131
|
execute: executeLspRename
|
|
5726
6132
|
},
|
|
6133
|
+
{
|
|
6134
|
+
name: "format",
|
|
6135
|
+
aliases: ["lsp_format"],
|
|
6136
|
+
title: "LSP Format",
|
|
6137
|
+
description: "Format a source file with its language server and write the returned edits to disk.",
|
|
6138
|
+
inputSchema: objectSchema({
|
|
6139
|
+
filePath: { type: "string", description: "Source file path to format." }
|
|
6140
|
+
}, ["filePath"]),
|
|
6141
|
+
execute: executeLspFormat
|
|
6142
|
+
},
|
|
5727
6143
|
{
|
|
5728
6144
|
name: "install_decision",
|
|
5729
6145
|
aliases: ["lsp_install_decision"],
|
|
@@ -5824,7 +6240,10 @@ function requestedProtocolVersion(params) {
|
|
|
5824
6240
|
var CONTEXT_KEY = "_context";
|
|
5825
6241
|
|
|
5826
6242
|
class InvalidDaemonRequestError extends Error {
|
|
5827
|
-
|
|
6243
|
+
constructor() {
|
|
6244
|
+
super(...arguments);
|
|
6245
|
+
this.name = "InvalidDaemonRequestError";
|
|
6246
|
+
}
|
|
5828
6247
|
}
|
|
5829
6248
|
function extractRequestContext(raw) {
|
|
5830
6249
|
if (!isPlainRecord(raw) || raw["method"] !== "tools/call")
|
|
@@ -5940,14 +6359,17 @@ async function callToolViaDaemon(name, args, options) {
|
|
|
5940
6359
|
function callDiagnosticsViaDaemon(filePath, options) {
|
|
5941
6360
|
return callToolViaDaemon("diagnostics", { filePath, severity: "error" }, options);
|
|
5942
6361
|
}
|
|
6362
|
+
function callFormatViaDaemon(filePath, options) {
|
|
6363
|
+
return callToolViaDaemon("format", { filePath }, options);
|
|
6364
|
+
}
|
|
5943
6365
|
function currentRequestContext(env = process.env) {
|
|
5944
6366
|
const cwd = process.cwd();
|
|
5945
6367
|
const home = env["HOME"] ?? homedir3();
|
|
5946
6368
|
return parseLspRequestContext({
|
|
5947
6369
|
cwd,
|
|
5948
|
-
projectConfigPaths: [
|
|
5949
|
-
userConfigPath:
|
|
5950
|
-
installDecisionsPath:
|
|
6370
|
+
projectConfigPaths: [join8(cwd, ".codex", "lsp-client.json")],
|
|
6371
|
+
userConfigPath: join8(home, ".codex", "lsp-client.json"),
|
|
6372
|
+
installDecisionsPath: join8(home, ".codex", "lsp-install-decisions.json"),
|
|
5951
6373
|
capabilities: { installDecisionTool: true }
|
|
5952
6374
|
});
|
|
5953
6375
|
}
|
|
@@ -5962,7 +6384,7 @@ function withContext(args, context) {
|
|
|
5962
6384
|
function ensureDaemonAvailable(paths, ensure, signal) {
|
|
5963
6385
|
if (!signal)
|
|
5964
6386
|
return ensure(paths);
|
|
5965
|
-
return new Promise((
|
|
6387
|
+
return new Promise((resolve, reject) => {
|
|
5966
6388
|
let settled = false;
|
|
5967
6389
|
const finish = (run) => {
|
|
5968
6390
|
if (settled)
|
|
@@ -5977,11 +6399,11 @@ function ensureDaemonAvailable(paths, ensure, signal) {
|
|
|
5977
6399
|
return;
|
|
5978
6400
|
}
|
|
5979
6401
|
signal.addEventListener("abort", onAbort, { once: true });
|
|
5980
|
-
Promise.resolve().then(() => ensure(paths, signal)).then(() => finish(() =>
|
|
6402
|
+
Promise.resolve().then(() => ensure(paths, signal)).then(() => finish(() => resolve()), (error) => finish(() => reject(signal.aborted ? new DaemonRequestCancelledError(false) : error)));
|
|
5981
6403
|
});
|
|
5982
6404
|
}
|
|
5983
6405
|
function sendToolCall(paths, token, name, args, options) {
|
|
5984
|
-
return new Promise((
|
|
6406
|
+
return new Promise((resolve, reject) => {
|
|
5985
6407
|
const socket = connect(paths.socket);
|
|
5986
6408
|
const requestId = allocateProxyRequestId();
|
|
5987
6409
|
let settled = false;
|
|
@@ -6034,7 +6456,7 @@ function sendToolCall(paths, token, name, args, options) {
|
|
|
6034
6456
|
}
|
|
6035
6457
|
const result = toToolResult(message, requestId);
|
|
6036
6458
|
if (result)
|
|
6037
|
-
finish(() =>
|
|
6459
|
+
finish(() => resolve(result));
|
|
6038
6460
|
else
|
|
6039
6461
|
finish(() => reject(new DaemonRequestError("invalid daemon response", requestWritten)));
|
|
6040
6462
|
});
|
|
@@ -6079,8 +6501,8 @@ function isRetryableTool(name) {
|
|
|
6079
6501
|
return name !== "rename" && name !== "lsp_rename";
|
|
6080
6502
|
}
|
|
6081
6503
|
// src/proxy.ts
|
|
6082
|
-
import { existsSync as
|
|
6083
|
-
import { basename as basename4, delimiter as delimiter4, dirname as
|
|
6504
|
+
import { existsSync as existsSync13, realpathSync as realpathSync6 } from "node:fs";
|
|
6505
|
+
import { basename as basename4, delimiter as delimiter4, dirname as dirname11, isAbsolute as isAbsolute6 } from "node:path";
|
|
6084
6506
|
var DEFAULT_STARTUP_TIMEOUT_MS = 1e4;
|
|
6085
6507
|
async function runMcpStdioProxy(options = {}) {
|
|
6086
6508
|
const input = options.input ?? process.stdin;
|
|
@@ -6203,34 +6625,34 @@ function canonicalizePathList(value) {
|
|
|
6203
6625
|
return value.split(delimiter4).map((entry) => canonicalizePath(entry) ?? entry).join(delimiter4);
|
|
6204
6626
|
}
|
|
6205
6627
|
function canonicalizePath(value) {
|
|
6206
|
-
if (value === undefined || !
|
|
6628
|
+
if (value === undefined || !isAbsolute6(value) || !existsSync13(value))
|
|
6207
6629
|
return value;
|
|
6208
|
-
return
|
|
6630
|
+
return realpathSync6(value);
|
|
6209
6631
|
}
|
|
6210
|
-
function projectRootFromOpenCodeConfigPath(
|
|
6211
|
-
if (basename4(
|
|
6632
|
+
function projectRootFromOpenCodeConfigPath(path) {
|
|
6633
|
+
if (basename4(path) !== "lsp.json" && basename4(path) !== "lsp-client.json")
|
|
6212
6634
|
return;
|
|
6213
|
-
const configDir =
|
|
6635
|
+
const configDir = dirname11(path);
|
|
6214
6636
|
const configDirName = basename4(configDir);
|
|
6215
6637
|
if (configDirName !== ".opencode" && configDirName !== ".omo")
|
|
6216
6638
|
return;
|
|
6217
|
-
return
|
|
6639
|
+
return dirname11(configDir);
|
|
6218
6640
|
}
|
|
6219
6641
|
export {
|
|
6220
|
-
|
|
6221
|
-
runMcpStdioProxy,
|
|
6222
|
-
resolveDaemonRuntime,
|
|
6223
|
-
probeDaemon,
|
|
6224
|
-
ensureDaemonRunning,
|
|
6225
|
-
disposeDefaultLspManager,
|
|
6226
|
-
daemonPaths,
|
|
6227
|
-
currentRequestContext,
|
|
6228
|
-
callToolViaDaemon,
|
|
6229
|
-
callDiagnosticsViaDaemon,
|
|
6230
|
-
OMO_LSP_DAEMON_VERSION,
|
|
6231
|
-
OMO_LSP_DAEMON_DIR,
|
|
6232
|
-
OMO_LSP_DAEMON_CLI,
|
|
6233
|
-
InvalidRuntimeOverrideError,
|
|
6642
|
+
InvalidDaemonDirectoryError,
|
|
6234
6643
|
InvalidDaemonVersionError,
|
|
6235
|
-
|
|
6644
|
+
InvalidRuntimeOverrideError,
|
|
6645
|
+
OMO_LSP_DAEMON_CLI,
|
|
6646
|
+
OMO_LSP_DAEMON_DIR,
|
|
6647
|
+
OMO_LSP_DAEMON_VERSION,
|
|
6648
|
+
callDiagnosticsViaDaemon,
|
|
6649
|
+
callToolViaDaemon,
|
|
6650
|
+
currentRequestContext,
|
|
6651
|
+
daemonPaths,
|
|
6652
|
+
disposeDefaultLspManager,
|
|
6653
|
+
ensureDaemonRunning,
|
|
6654
|
+
probeDaemon,
|
|
6655
|
+
resolveDaemonRuntime,
|
|
6656
|
+
runMcpStdioProxy,
|
|
6657
|
+
validateDaemonVersion
|
|
6236
6658
|
};
|