semantic-js-mcp 0.8.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -0,0 +1,25 @@
1
+ {
2
+ "name": "semantic-js-mcp",
3
+ "version": "0.8.0",
4
+ "description": "Semantic understanding of JavaScript codebases for AI agents",
5
+ "author": {
6
+ "name": "Jonathan Muñoz Lucas"
7
+ },
8
+ "license": "MIT",
9
+ "keywords": ["lsp", "mcp", "javascript", "typescript", "vue", "semantic-analysis", "code-navigation"],
10
+ "skills": "./skills/",
11
+ "mcpServers": "./.mcp.json",
12
+ "interface": {
13
+ "displayName": "Semantic JS MCP",
14
+ "shortDescription": "Semantic understanding of JavaScript codebases for AI agents",
15
+ "longDescription": "Adds read-only, workspace-aware TypeScript, JavaScript, Node module, JSX, TSX, and Vue evidence using language servers, complete reference accounting, reusable paged collections, actionable unresolved candidates, and versioned diagnostics.",
16
+ "developerName": "Jonathan Muñoz Lucas",
17
+ "category": "Developer Tools",
18
+ "capabilities": ["Read"],
19
+ "defaultPrompt": [
20
+ "Trace this TypeScript symbol and its callers.",
21
+ "Review this change using semantic references.",
22
+ "Check focused diagnostics for the edited files."
23
+ ]
24
+ }
25
+ }
package/.mcp.json ADDED
@@ -0,0 +1,12 @@
1
+ {
2
+ "mcpServers": {
3
+ "semantic-js-mcp": {
4
+ "command": "node",
5
+ "args": ["./server.mjs"],
6
+ "cwd": ".",
7
+ "startup_timeout_sec": 30,
8
+ "tool_timeout_sec": 300,
9
+ "default_tools_approval_mode": "auto"
10
+ }
11
+ }
12
+ }
@@ -0,0 +1,9 @@
1
+ {
2
+ "bracketSpacing": false,
3
+ "printWidth": 140,
4
+ "proseWrap": "preserve",
5
+ "semi": true,
6
+ "singleQuote": false,
7
+ "tabWidth": 2,
8
+ "trailingComma": "all"
9
+ }
package/CHANGELOG.md ADDED
@@ -0,0 +1,29 @@
1
+ # Changelog
2
+
3
+ All notable changes to this project will be documented in this file.
4
+
5
+ ## [Unreleased]
6
+
7
+ ## [0.8.0] - 2026-07-15
8
+
9
+ ### Added
10
+
11
+ - Initial pre-release of the read-only semantic evidence server for TypeScript, JavaScript, TSX, JSX, Node module variants, and Vue.
12
+ - Definition, hover, diagnostics, document-symbol, workspace-symbol, named-symbol audit, position audit, and verified-reference tools.
13
+ - Repository-wide text-match accounting that separates requested-symbol matches, different symbols, and unresolved candidates.
14
+ - Explicit collection, presentation, completeness, and diagnostic-trust states.
15
+ - Paged reference collections with content and repository-inventory freshness validation.
16
+ - Workspace-aware TypeScript and Vue language-server selection with cross-workspace reference verification.
17
+ - Vue template fallback for locally imported component bindings and signature recovery from resolved declarations.
18
+ - Visible server and result-schema identity in canonical responses.
19
+ - Runtime checks, generic TypeScript and Vue smoke fixtures, canonical-input CI policy evaluation, and reproducible benchmarks.
20
+ - Literal `not-reported` diagnostic severity when a language server omits severity instead of silently assigning another severity.
21
+ - Codex plugin metadata, semantic-navigation skill, architecture decisions, contribution guide, security policy, and public roadmap.
22
+ - `semantic-js-mcp` executable with `serve`, `doctor`, version, help, JSON, and YAML output paths.
23
+ - Deterministic installation doctor for runtime requirements, provider resolution, MCP startup, tool discovery, TypeScript evidence, diagnostic freshness, and Vue navigation.
24
+ - Explicit npm package allowlist and an isolated tarball installation smoke that prevents runtime reuse of the source checkout.
25
+ - Reproducible Prettier formatting with a repository-wide public-source check in the validation gate.
26
+
27
+ ### Changed
28
+
29
+ - Runtime provider entry points resolve through Node's package resolution algorithm so npm dependency hoisting is supported.
@@ -0,0 +1,64 @@
1
+ # Contributing
2
+
3
+ Semantic JS MCP is pre-release. Changes should preserve its read-only evidence contract and keep collection scope separate from response presentation.
4
+
5
+ ## Requirements
6
+
7
+ - Node.js 22 or newer;
8
+ - npm with lockfile support;
9
+ - `rg` available on `PATH`.
10
+
11
+ ## Setup
12
+
13
+ ```bash
14
+ npm ci
15
+ npm run format:check
16
+ npm run check
17
+ npm run check:runtime
18
+ npm run doctor
19
+ npm run smoke:ci
20
+ npm run smoke
21
+ npm run smoke:vue
22
+ ```
23
+
24
+ Run `npm run benchmark` for changes that affect repository scanning, reference verification, caching, lifecycle, or memory.
25
+
26
+ ## Source Of Truth
27
+
28
+ - `protocol.mjs` owns public literals, server identity, schema identity, runtime components, and defaults.
29
+ - `.prettierrc.json` and the `format` scripts define the public source style.
30
+ - `skills/semantic-navigation/references/protocol-literals.md` is generated; update it with `node scripts/generate-protocol-reference.mjs`.
31
+ - `README.md` documents implemented behavior and known limitations.
32
+ - `ROADMAP.md` summarizes public development direction without defining implemented behavior.
33
+
34
+ ## Change Expectations
35
+
36
+ - Centralize public literals in `protocol.mjs`.
37
+ - Run `npm run format` after changing public source or documentation.
38
+ - Regenerate protocol documentation instead of editing it directly.
39
+ - Add isolated fixtures for positive, partial, and failed evidence.
40
+ - Preserve explicit unresolved candidates and freshness status.
41
+ - Avoid project-specific assumptions in the public MCP or skill.
42
+ - Do not commit `node_modules`, local caches, credentials, or third-party source.
43
+
44
+ ## Validation Expectations
45
+
46
+ Run the smallest relevant checks while developing, then run the complete local validation suite before submitting a change:
47
+
48
+ ```bash
49
+ npm run check
50
+ npm run check:runtime
51
+ npm run smoke:ci
52
+ npm run smoke
53
+ npm run smoke:vue
54
+ npm run smoke:distribution
55
+ ```
56
+
57
+ Also run `npm run benchmark` when collection cost or memory could change. Run `npm run doctor` when changing runtime resolution, provider startup, the CLI, or diagnostic trust. New behavior should use generic fixtures and cover complete, partial, limited, failed, stale, or untrusted outcomes as applicable.
58
+
59
+ ## Changelog And Versioning
60
+
61
+ - Add user-visible behavior under `Unreleased` while developing.
62
+ - Move those entries to a dated version section when the package version is finalized.
63
+ - Increment the result-schema version when consumers must understand a changed canonical response shape or identity.
64
+ - A server-version change does not automatically require a result-schema change when the response contract remains compatible.
package/LICENSE ADDED
@@ -0,0 +1,21 @@
1
+ MIT License
2
+
3
+ Copyright (c) 2026 Jonathan Muñoz Lucas
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.
package/README.md ADDED
@@ -0,0 +1,278 @@
1
+ # Semantic JS MCP
2
+
3
+ **Your coding agent is only as good as its understanding of your codebase.**
4
+
5
+ Coding agents can generate code quickly, but reliable engineering requires more than reading files and matching text. They need to understand which declaration a reference belongs to, how symbols cross workspace boundaries, whether the collected evidence is complete, and whether that evidence is still accurate.
6
+
7
+ Semantic JS MCP gives coding agents structured, read-only semantic context so they can navigate, review, and change code with explicit uncertainty.
8
+
9
+ **Better agents begin with better evidence.**
10
+
11
+ It supports the JavaScript ecosystem, including TypeScript, JavaScript, TSX, JSX, Node module variants, and Vue projects. Language servers provide the underlying semantic data, which the server turns into structured results designed for coding agents.
12
+
13
+ For each file, it identifies the owning workspace and uses the corresponding TypeScript or Vue language server. Across the repository, it can distinguish verified references from unrelated or unresolved text matches. These results complement text search, source inspection, and focused tests.
14
+
15
+ ## Project Status
16
+
17
+ Version `0.8.0` is the first public release. APIs and result contracts may evolve while the project remains on the `0.x` release line. See the [roadmap](ROADMAP.md) for areas under consideration.
18
+
19
+ ## Installation
20
+
21
+ ### Codex plugin
22
+
23
+ Add the public marketplace, then install the plugin:
24
+
25
+ ```bash
26
+ codex plugin marketplace add elnonathan/semantic-js-mcp
27
+ codex plugin add semantic-js-mcp@elnonathan
28
+ ```
29
+
30
+ Start a new Codex session after installation. The plugin bundles both the MCP server configuration and the semantic-navigation skill.
31
+
32
+ ### MCP executable
33
+
34
+ Install the package globally when using an MCP host that accepts a command-based stdio configuration:
35
+
36
+ ```bash
37
+ npm install --global semantic-js-mcp
38
+ semantic-js-mcp doctor
39
+ ```
40
+
41
+ Configure the host to run `semantic-js-mcp serve`.
42
+
43
+ ## Runtime
44
+
45
+ - Node.js 22 or newer is supported.
46
+ - Node.js 24 LTS is recommended for new installations. See the [Node.js release schedule](https://nodejs.org/en/about/previous-releases).
47
+ - `rg` (ripgrep) must be available on `PATH` for repository-wide discovery.
48
+ - The nearest workspace TypeScript SDK is used when available; the bundled TypeScript SDK is the fallback.
49
+ - TypeScript, `typescript-language-server`, and the Vue language server are pinned dependencies. Install with `npm ci`; startup verifies their bundled entry points before accepting MCP requests.
50
+ - Source discovery and language selection include `.ts`, `.tsx`, `.mts`, `.cts`, `.js`, `.jsx`, `.mjs`, `.cjs`, and `.vue` files.
51
+ - Run `npm run check:runtime` to report every required component and its resolved file path.
52
+
53
+ The package exposes a `semantic-js-mcp` executable. `semantic-js-mcp serve` starts the stdio MCP server, and `semantic-js-mcp doctor` verifies the installed Node runtime, ripgrep, resolved provider paths, MCP startup, tool discovery, TypeScript reference accounting, diagnostic freshness, and Vue navigation.
54
+
55
+ ## Development Setup
56
+
57
+ From a source checkout:
58
+
59
+ ```bash
60
+ npm ci
61
+ npm run check
62
+ npm run check:runtime
63
+ npm run doctor
64
+ npm run smoke:ci
65
+ npm run smoke
66
+ npm run smoke:vue
67
+ ```
68
+
69
+ Run `npm run benchmark` after changes to scanning, references, caching, lifecycle, or memory. Normal analysis is local and read-only; it does not require network access after dependencies are installed.
70
+
71
+ For an MCP host that accepts a direct stdio configuration, point it at the checked-out server using an absolute path:
72
+
73
+ ```json
74
+ {
75
+ "mcpServers": {
76
+ "semantic-js-mcp": {
77
+ "command": "node",
78
+ "args": ["/absolute/path/to/semantic-js-mcp/server.mjs"]
79
+ }
80
+ }
81
+ }
82
+ ```
83
+
84
+ The bundled [`.mcp.json`](.mcp.json) provides the relative-path configuration used when the repository is installed as a Codex plugin.
85
+
86
+ When the package executable is available on the host's `PATH`, the equivalent stdio configuration is:
87
+
88
+ ```json
89
+ {
90
+ "mcpServers": {
91
+ "semantic-js-mcp": {
92
+ "command": "semantic-js-mcp",
93
+ "args": ["serve"]
94
+ }
95
+ }
96
+ }
97
+ ```
98
+
99
+ ## Tool Graph
100
+
101
+ Tools are ordered from smaller responses to deeper evidence:
102
+
103
+ | Tool | Provides | Typical continuation |
104
+ | ------------------------------- | --------------------------------------------------------- | -------------------------------------------------- |
105
+ | `lsp_document_symbols` | Structure for one file | `lsp_definition`, `lsp_audit_symbol` |
106
+ | `lsp_workspace_symbols` | Symbol-name discovery | `lsp_count_named_symbol`, `lsp_audit_named_symbol` |
107
+ | `lsp_definition` | Definition resolution at a position | `lsp_hover`, `lsp_count_references` |
108
+ | `lsp_hover` | Inferred type and documentation | `lsp_definition`, `lsp_audit_symbol` |
109
+ | `lsp_diagnostics` | Focused diagnostics for one file | `lsp_definition`, `lsp_hover` |
110
+ | `lsp_count_text_matches` | Exact identifier text count without semantic verification | `lsp_count_named_symbol`, `lsp_audit_named_symbol` |
111
+ | `lsp_count_named_symbol` | Definition and reference counts by name | `lsp_audit_named_symbol`, `lsp_references` |
112
+ | `lsp_count_references` | Reference counts at a position | `lsp_audit_symbol`, `lsp_references` |
113
+ | `lsp_audit_named_symbol` | Composed summary by symbol name | `lsp_references` |
114
+ | `lsp_audit_symbol` | Composed summary at a position | `lsp_references` |
115
+ | `lsp_references` | First page of verified locations | `lsp_reference_page` |
116
+ | `lsp_reference_page` | A later page from the same collection | `lsp_definition` |
117
+ | `lsp_unresolved_reference_page` | Unresolved candidates with locations and literal reasons | `lsp_definition` |
118
+
119
+ Composite audits reuse the same internal definition, hover, and reference primitives as the narrow tools. Compatible count, audit, and reference calls reuse a short-lived reference set.
120
+
121
+ ## Result Contract
122
+
123
+ Every successful result contains:
124
+
125
+ - `server`: the literal semantic-js-mcp server name and version that produced the response.
126
+ - `resultSchema`: the literal canonical result schema name and version.
127
+ - `request`: normalized inputs and explicit limit interpretation.
128
+ - `result`: evidence produced by the tool.
129
+ - `collection`: how evidence collection completed.
130
+ - `presentation`: how much collected evidence appears in this response.
131
+ - `continueWith`: exact MCP tool names that can add the next kind of evidence.
132
+
133
+ `structuredContent` is the canonical JSON object. The text content is YAML generated from that same object and parses back to the same data.
134
+
135
+ ### Collection status
136
+
137
+ - `complete`: the requested collection scope completed and every discovered item was classified.
138
+ - `limited`: a supplied `maxCandidates` or `maxDefinitions` value stopped collection.
139
+ - `partial`: collection completed with explicitly reported items whose definition or owning file could not be resolved.
140
+ - `failed`: the tool call failed and the error object explains why.
141
+
142
+ Collection and presentation are independent. A complete collection may use `presentation.mode: page`, `count-only`, `summary-by-file`, or `subset` without weakening its counts.
143
+
144
+ For reference results, `includeDeclaration: false` excludes locations that resolve to the requested declaration. It never excludes the source position merely because that position initiated the query. The reported invariant is `verifiedTotal = foundByOwningWorkspaceLanguageServer + verifiedFromOtherWorkspaces` after declaration filtering and deduplication.
145
+
146
+ ### Vue template definitions
147
+
148
+ Definition lookup uses the Vue language server and TypeScript server first. If both leave a Vue template tag unresolved, the server parses the SFC and follows only a matching local import from `<script>` or `<script setup>`. A successful fallback reports `resolutionMethod: vue-template-import-binding-definition`. This proves an imported component binding; it does not infer global component registration or filename-based identity.
149
+
150
+ The Vue parser and TypeScript AST dependencies are loaded lazily only when this fallback is needed.
151
+
152
+ ### Signature source
153
+
154
+ Position audits first request hover information at the query position. If that position has a resolved definition but no hover information, the audit requests hover at the resolved declaration. `signatureSource` reports `query-position-hover`, `resolved-definition-hover`, or `not-reported`; `signatureDefinition` identifies the declaration used by the fallback.
155
+
156
+ ### Limits
157
+
158
+ Collection limits accept positive integers only:
159
+
160
+ - omitted: `{mode: unlimited}`
161
+ - supplied: `{mode: maximum, maximum: N}`
162
+
163
+ Omitting `maxCandidates` or `maxDefinitions` requests unlimited collection. `pageSize` and `maxResults` only control returned items for tools that expose them as presentation parameters.
164
+
165
+ ### Text-match accounting
166
+
167
+ Repository verification reports:
168
+
169
+ - `matchesFound`
170
+ - `matchesChecked`
171
+ - `matchesToRequestedSymbol`
172
+ - `matchesToDifferentSymbols`
173
+ - `matchesWhoseDefinitionCouldNotBeResolved`
174
+ - `accountingStatus: complete | incomplete`
175
+
176
+ `accountingStatus: complete` means every discovered text match appears in exactly one classification. Unresolved matches remain explicit and make semantic collection `partial`.
177
+
178
+ Count and audit responses expose the `referenceSetId` and unresolved-candidate count. Use `lsp_unresolved_reference_page` to inspect those candidates without inflating every summary. The server also queries tsserver `projectInfo` for unresolved candidates and reports whether the file belongs to a configured or inferred TypeScript project. Reasons describe only observed behavior; they do not speculate that an alias caused a failure.
179
+
180
+ ### Freshness
181
+
182
+ Reusable reference sets store SHA-256 fingerprints for the source file, native reference files, every cross-workspace candidate file, and the relevant `package.json`, `tsconfig.json`, or `jsconfig.json` files. They also store a repository source-inventory fingerprint built from every relevant path, file size, and high-resolution modification time. Reuse and pagination verify both layers, so new, deleted, renamed, or normally modified source files invalidate repository-wide completeness. Changed evidence produces `REFERENCE_SET_CONTENT_CHANGED` and requires a new `lsp_references` collection. Expired or evicted sets produce `REFERENCE_SET_NOT_FOUND_OR_EXPIRED`.
183
+
184
+ The inventory is sampled before and after collection. If repository sources change during collection, the server retries once and then returns `REPOSITORY_CHANGED_DURING_COLLECTION` instead of publishing an unstable result.
185
+
186
+ Diagnostics clear their cache on `didChange` and report the analyzed document version and SHA-256 content fingerprint. Only a language-server report for that exact document version appears under `diagnosticsForCurrentDocument`. Otherwise that field is `null`, `evidence.status` is `untrusted`, and any unconfirmed report is isolated under `unconfirmedDiagnosticReport`. Untrusted diagnostics always produce a partial collection.
187
+
188
+ Diagnostic severities are preserved literally. If a language server omits severity, the result reports `not-reported`; it is not silently treated as information, warning, or error.
189
+
190
+ ### CI policy adapter
191
+
192
+ MCP tools report evidence; they do not decide whether a code change passes. `npm run ci:evaluate -- <result.json>` applies a deterministic CI policy to one canonical structured result:
193
+
194
+ - `pass`, exit `0`: complete evidence and no verified error diagnostic.
195
+ - `fail`, exit `1`: verified diagnostics contain an error.
196
+ - `untrusted`, exit `2`: collection is partial or limited.
197
+ - `blocked`, exit `3`: the tool failed or the input is not a semantic-js-mcp result.
198
+
199
+ Pass `--yaml` after the input path for a YAML representation. The adapter accepts canonical JSON or YAML, validates the server and result-schema identity plus public tool and presentation literals, and never converts incomplete evidence into a pass.
200
+
201
+ ### Installation doctor
202
+
203
+ `semantic-js-mcp doctor` returns a structured installation report with the same deterministic status vocabulary and exit codes as the CI adapter:
204
+
205
+ - `pass`, exit `0`: every installation and semantic fixture check passed;
206
+ - `fail`, exit `1`: the server ran, but a functional check returned the wrong result;
207
+ - `untrusted`, exit `2`: runtime checks passed, but a provider did not confirm current diagnostic evidence;
208
+ - `blocked`, exit `3`: a runtime requirement, provider component, or MCP startup step was unavailable.
209
+
210
+ Use `semantic-js-mcp doctor --yaml` for a YAML representation. An `untrusted` result is not converted to a package failure by the distribution smoke test, but the reason remains explicit in the report.
211
+
212
+ ### Cost visibility
213
+
214
+ `lsp_count_text_matches` scans repository text without issuing per-match semantic requests. Use it to measure common identifiers before requesting verified counts or audits. Semantic collections preserve omitted limits as unlimited and report text-search time, semantic-verification time, semantic request count, and maximum concurrency. There is no hidden candidate cap.
215
+
216
+ The bundled Codex MCP configuration allows up to 300 seconds for one tool call. Reaching a client or language-server timeout returns a failed call; it never changes collection scope or reports a timed-out collection as complete.
217
+
218
+ ## Memory Management
219
+
220
+ Language-server clients and reusable reference sets are released automatically using idle timeout, TTL, and LRU policies. These policies affect reuse only; they do not cap a collection being computed.
221
+
222
+ Environment variables:
223
+
224
+ - `SEMANTIC_JS_MCP_CLIENT_IDLE_TIMEOUT_MS` default `60000`
225
+ - `SEMANTIC_JS_MCP_CLIENT_MINIMUM_EVICTION_AGE_MS` default `15000`
226
+ - `SEMANTIC_JS_MCP_MAXIMUM_ACTIVE_CLIENTS` default `4`
227
+ - `SEMANTIC_JS_MCP_REFERENCE_SET_TTL_MS` default `300000`
228
+ - `SEMANTIC_JS_MCP_MAXIMUM_REFERENCE_SETS` default `12`
229
+ - `SEMANTIC_JS_MCP_MAXIMUM_CHANGED_REFERENCE_SET_MARKERS` default `24`
230
+ - `SEMANTIC_JS_MCP_MAXIMUM_CACHED_REFERENCE_LOCATIONS` default `50000`
231
+ - `SEMANTIC_JS_MCP_DEFAULT_REFERENCE_PAGE_SIZE` default `100`
232
+ - `SEMANTIC_JS_MCP_CROSS_WORKSPACE_CONCURRENCY` default `6`
233
+
234
+ A single reference collection may exceed the cache-location budget so it can still be paged. Older collections are evicted first.
235
+
236
+ ## Verification
237
+
238
+ ```bash
239
+ npm run check
240
+ npm run check:runtime
241
+ npm run doctor
242
+ npm run smoke
243
+ npm run smoke:ci
244
+ npm run smoke:vue
245
+ npm run smoke:distribution
246
+ ```
247
+
248
+ `npm run benchmark` measures text counting, verified reference collection, memory, and freshness-validation latency at configurable match counts. Set `SEMANTIC_JS_MCP_BENCHMARK_COUNTS=10,100,1000,10000` to include the 10,000-match scale.
249
+
250
+ `npm run smoke:distribution` packs the explicit npm file allowlist, installs the tarball into a temporary consumer project, runs the installed executable, and verifies that runtime components resolve from the consumer dependency tree rather than the source checkout.
251
+
252
+ The smoke tests create temporary generic TypeScript and Vue projects. They do not depend on a specific application repository.
253
+
254
+ ## Current Limitations
255
+
256
+ - The server provides static semantic evidence, not runtime call tracing or behavioral proof.
257
+ - Empty references and clean diagnostics do not establish absence or correctness.
258
+ - Vue named-component discovery remains ambiguous when filenames, component names, import aliases, global registration, and test doubles differ. Prefer a position-based audit when an exact use is available.
259
+ - Diagnostics remain `untrusted` when the owning language server does not correlate a report with the current document version.
260
+ - Dynamic imports, computed property access, generated code, runtime dependency injection, and dynamically constructed class names may require text search and direct source inspection.
261
+ - CSS graph analysis, Tailwind semantics, and other language domains are intentionally outside this project. Provider-native diagnostics embedded in Vue documents may still be preserved.
262
+
263
+ ## Roadmap
264
+
265
+ See [ROADMAP.md](ROADMAP.md) for planned areas of development. Roadmap items describe direction, not release commitments.
266
+
267
+ ## Project Documents
268
+
269
+ - [Architecture decisions](docs/architecture-decisions.md)
270
+ - [Distribution verification](docs/distribution.md)
271
+ - [Roadmap](ROADMAP.md)
272
+ - [Changelog](CHANGELOG.md)
273
+ - [Contributing](CONTRIBUTING.md)
274
+ - [Security policy](SECURITY.md)
275
+
276
+ ## Maintainer
277
+
278
+ [Jonathan Muñoz Lucas](https://mx.linkedin.com/in/nonathan)
package/ROADMAP.md ADDED
@@ -0,0 +1,37 @@
1
+ # Roadmap
2
+
3
+ Semantic JS MCP is under active development. This roadmap outlines areas of investigation and intended development. Items are directional and are not release commitments.
4
+
5
+ ## Reliability
6
+
7
+ - Improve current-document diagnostic confirmation across supported language servers.
8
+ - Keep semantic evidence fresh across edits, file additions, removals, renames, and workspace configuration changes.
9
+ - Expand deterministic fixtures for complete, partial, limited, failed, stale, and untrusted outcomes.
10
+ - Continue measuring collection latency, memory use, and language-server lifecycle behavior at repository scale.
11
+
12
+ ## Vue
13
+
14
+ - Improve named-component discovery for single-file components.
15
+ - Expand template binding resolution while preserving explicit uncertainty for global or dynamic registration.
16
+ - Improve diagnostics and signature recovery in complex Vue files.
17
+
18
+ ## React And JSX
19
+
20
+ - Add framework-focused fixtures for components, hooks, props, re-exports, aliases, and higher-order patterns.
21
+ - Document the evidence boundaries for dynamic JSX composition and runtime component selection.
22
+
23
+ ## Agent-Facing Results
24
+
25
+ - Keep result vocabulary literal, finite, and versioned.
26
+ - Improve compact presentation without hiding collection scope or unresolved evidence.
27
+ - Expand examples for combining count, audit, reference, diagnostic, text-search, source-inspection, and test evidence.
28
+
29
+ ## Distribution
30
+
31
+ - Expand reproducible package and plugin release checks across supported Node.js LTS releases and hosted CI.
32
+ - Document setup for additional MCP hosts using the same public server contract.
33
+ - Add immutable release-source, upgrade, rollback, and installed-plugin verification.
34
+
35
+ ## Additional Language Domains
36
+
37
+ CSS, preprocessors, utility-class frameworks, and other language domains may be explored as independent providers. Any expansion must preserve source attribution, explicit uncertainty, and the read-only evidence contract.
package/SECURITY.md ADDED
@@ -0,0 +1,22 @@
1
+ # Security Policy
2
+
3
+ Semantic JS MCP is a read-only developer tool that starts bundled language servers and reads local source files. It must not apply workspace edits, execute repository-provided commands, require credentials, or use network access during normal local analysis.
4
+
5
+ ## Supported Versions
6
+
7
+ During pre-release development, security fixes are applied to the latest version only.
8
+
9
+ ## Reporting A Vulnerability
10
+
11
+ Report vulnerabilities privately using the maintainer address in `package.json` or GitHub private vulnerability reporting when available. Do not open a public issue for an unpatched vulnerability.
12
+
13
+ Do not include repository credentials, proprietary source, access tokens, or other secrets in a report.
14
+
15
+ Include:
16
+
17
+ - semantic-js-mcp version;
18
+ - Node.js version;
19
+ - operating system;
20
+ - affected tool;
21
+ - minimal reproduction using non-sensitive source;
22
+ - observed and expected behavior.
package/cli.mjs ADDED
@@ -0,0 +1,45 @@
1
+ #!/usr/bin/env node
2
+
3
+ import {stringify as stringifyYaml} from "yaml";
4
+ import {CLI_ARGUMENT, CLI_COMMAND, CLI_MESSAGE, DEFAULT, PROCESS_EXIT_CODE, PRODUCT, SERVER_VERSION} from "./protocol.mjs";
5
+
6
+ const HELP = `Usage: ${PRODUCT.NAME} [command] [options]
7
+
8
+ Commands:
9
+ ${CLI_COMMAND.SERVE} Start the MCP server over stdio (default)
10
+ ${CLI_COMMAND.DOCTOR} Verify the installed runtime and semantic providers
11
+
12
+ Options:
13
+ ${CLI_ARGUMENT.YAML} Render doctor output as YAML instead of JSON
14
+ ${CLI_ARGUMENT.HELP}, ${CLI_ARGUMENT.HELP_SHORT} Show this help
15
+ ${CLI_ARGUMENT.VERSION}, ${CLI_ARGUMENT.VERSION_SHORT} Show the installed version
16
+ `;
17
+
18
+ const args = process.argv.slice(DEFAULT.PROCESS_ARGUMENT_OFFSET);
19
+ const commandIndex = args.findIndex((argument) => !argument.startsWith("-"));
20
+ const command = commandIndex >= 0 ? args[commandIndex] : CLI_COMMAND.SERVE;
21
+ const commandArguments = args.filter((_, index) => index !== commandIndex);
22
+ const acceptedArguments = command === CLI_COMMAND.DOCTOR ? new Set([CLI_ARGUMENT.YAML]) : new Set();
23
+ const unknownArguments = commandArguments.filter((argument) => !acceptedArguments.has(argument));
24
+
25
+ if (args.includes(CLI_ARGUMENT.HELP) || args.includes(CLI_ARGUMENT.HELP_SHORT) || command === CLI_COMMAND.HELP) {
26
+ process.stdout.write(HELP);
27
+ } else if (args.includes(CLI_ARGUMENT.VERSION) || args.includes(CLI_ARGUMENT.VERSION_SHORT) || command === CLI_COMMAND.VERSION) {
28
+ process.stdout.write(`${SERVER_VERSION}\n`);
29
+ } else if (args.length > 0 && commandIndex < 0) {
30
+ process.stderr.write(`${CLI_MESSAGE.UNKNOWN_OPTION}: ${args[0]}\n\n${HELP}`);
31
+ process.exitCode = PROCESS_EXIT_CODE.FAILURE;
32
+ } else if (unknownArguments.length > 0) {
33
+ process.stderr.write(`${CLI_MESSAGE.UNKNOWN_ARGUMENT}: ${unknownArguments[0]}\n\n${HELP}`);
34
+ process.exitCode = PROCESS_EXIT_CODE.FAILURE;
35
+ } else if (command === CLI_COMMAND.SERVE) {
36
+ await import("./server.mjs");
37
+ } else if (command === CLI_COMMAND.DOCTOR) {
38
+ const {runDoctor} = await import("./lib/doctor.mjs");
39
+ const result = await runDoctor();
40
+ process.stdout.write(args.includes(CLI_ARGUMENT.YAML) ? stringifyYaml(result, {lineWidth: 0}) : `${JSON.stringify(result, null, 2)}\n`);
41
+ process.exitCode = result.exitCode;
42
+ } else {
43
+ process.stderr.write(`${CLI_MESSAGE.UNKNOWN_COMMAND}: ${command}\n\n${HELP}`);
44
+ process.exitCode = PROCESS_EXIT_CODE.FAILURE;
45
+ }
@@ -0,0 +1,72 @@
1
+ # Architecture Decisions
2
+
3
+ This document records accepted product boundaries. These decisions may be revised through an explicit change that documents the reason and migration impact.
4
+
5
+ ## DEC-001: Independent MCPs By Semantic Domain
6
+
7
+ Status: accepted
8
+
9
+ Semantic support for JavaScript, CSS, PHP, and other domains belongs in independent projects with separate dependencies, processes, releases, installation, and lifecycle management.
10
+
11
+ This project is `semantic-js-mcp`; it does not load or bundle semantic providers for other domains.
12
+
13
+ ## DEC-002: Composition Belongs To The Consumer
14
+
15
+ Status: accepted
16
+
17
+ One MCP does not call another MCP. A model, skill, CI adapter, or other consumer decides whether evidence from multiple semantic domains is needed.
18
+
19
+ This avoids runtime coupling, chained failures, implicit configuration, and assumptions that another product exists.
20
+
21
+ ## DEC-003: Common Representation, Domain-Specific Evidence
22
+
23
+ Status: accepted
24
+
25
+ Related semantic MCPs should use a compatible evidence envelope when practical:
26
+
27
+ - server identity;
28
+ - result-schema identity;
29
+ - tool and normalized request;
30
+ - result;
31
+ - collection status;
32
+ - presentation status;
33
+ - exact continuation tool names.
34
+
35
+ Each domain owns the vocabulary inside its result. A CSS class relationship is not represented as a JavaScript LSP reference.
36
+
37
+ ## DEC-004: Continuations Stay Inside One MCP
38
+
39
+ Status: accepted
40
+
41
+ `continueWith` names tools from the server that produced the response. It does not recommend tools from another MCP. Cross-product guidance belongs in consumer documentation or skills.
42
+
43
+ ## DEC-005: Narrow And Composed Tools Coexist
44
+
45
+ Status: accepted
46
+
47
+ Narrow tools provide one focused fact with a small response. Composed audits reuse the same internal primitives to reduce tool calls for consumers that can use a larger evidence summary.
48
+
49
+ Composed tools do not remove access to narrow tools and do not weaken collection accounting.
50
+
51
+ ## DEC-006: Preserve Provider-Native Embedded Evidence
52
+
53
+ Status: accepted
54
+
55
+ The JavaScript ecosystem includes mixed-language documents. When the owning provider reports diagnostics for a Vue template or embedded CSS, SCSS, or Less block, semantic-js-mcp preserves that evidence instead of filtering it according to another provider's domain.
56
+
57
+ Where it can be determined safely, diagnostic evidence should identify:
58
+
59
+ - provider;
60
+ - document language;
61
+ - embedded region;
62
+ - embedded language.
63
+
64
+ Unknown provenance remains explicit. Provider-native style diagnostics do not imply complete CSS graph analysis.
65
+
66
+ ## DEC-007: Extract Shared Code Only After A Second Implementation
67
+
68
+ Status: accepted
69
+
70
+ The project may document transferable concepts, but it will not create a shared runtime package or universal provider framework before a second semantic MCP demonstrates concrete duplication.
71
+
72
+ Compatibility should begin with result concepts and conformance fixtures, not premature runtime coupling.