@cyanheads/cyanheads-mcp-server 0.4.1 → 0.4.3
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/AGENTS.md +56 -26
- package/CLAUDE.md +56 -26
- package/Dockerfile +38 -29
- package/README.md +59 -48
- package/changelog/0.4.x/0.4.2.md +32 -0
- package/changelog/0.4.x/0.4.3.md +34 -0
- package/changelog/template.md +9 -26
- package/dist/index.js +22 -1
- package/dist/index.js.map +1 -1
- package/dist/mcp-server/tools/definitions/describe-entry.tool.d.ts +24 -0
- package/dist/mcp-server/tools/definitions/describe-entry.tool.d.ts.map +1 -1
- package/dist/mcp-server/tools/definitions/describe-entry.tool.js +120 -95
- package/dist/mcp-server/tools/definitions/describe-entry.tool.js.map +1 -1
- package/dist/mcp-server/tools/definitions/search-catalog.tool.d.ts +12 -0
- package/dist/mcp-server/tools/definitions/search-catalog.tool.d.ts.map +1 -1
- package/dist/mcp-server/tools/definitions/search-catalog.tool.js +86 -20
- package/dist/mcp-server/tools/definitions/search-catalog.tool.js.map +1 -1
- package/dist/services/catalog/catalog-service.d.ts +2 -2
- package/dist/services/catalog/catalog-service.d.ts.map +1 -1
- package/dist/services/catalog/catalog-service.js +36 -11
- package/dist/services/catalog/catalog-service.js.map +1 -1
- package/dist/services/catalog/remote-catalog-provider.d.ts +2 -2
- package/dist/services/catalog/remote-catalog-provider.d.ts.map +1 -1
- package/dist/services/catalog/remote-catalog-provider.js +34 -5
- package/dist/services/catalog/remote-catalog-provider.js.map +1 -1
- package/dist/services/catalog/self-record.js +3 -3
- package/dist/services/catalog/service-instance.js +1 -1
- package/dist/services/catalog/service-instance.js.map +1 -1
- package/dist/services/catalog/types.d.ts +2 -2
- package/dist/services/catalog/types.d.ts.map +1 -1
- package/manifest.json +2 -2
- package/package.json +26 -14
- package/server.json +3 -3
package/README.md
CHANGED
|
@@ -7,13 +7,13 @@
|
|
|
7
7
|
|
|
8
8
|
<div align="center">
|
|
9
9
|
|
|
10
|
-
[](./CHANGELOG.md) [](./LICENSE) [](https://github.com/users/cyanheads/packages/container/package/cyanheads-mcp-server) [](https://modelcontextprotocol.io/) [](https://www.npmjs.com/package/@cyanheads/cyanheads-mcp-server) [](https://www.typescriptlang.org/) [](https://bun.sh/)
|
|
11
11
|
|
|
12
12
|
</div>
|
|
13
13
|
|
|
14
14
|
<div align="center">
|
|
15
15
|
|
|
16
|
-
[](https://github.com/cyanheads/cyanheads-mcp-server/releases/latest/download/cyanheads-mcp-server.mcpb) [](https://cursor.com/en/install-mcp?name=cyanheads-mcp-server&config=eyJjb21tYW5kIjoibnB4IiwiYXJncyI6WyIteSIsIkBjeWFuaGVhZHMvY3lhbmhlYWRzLW1jcC1zZXJ2ZXIiXX0=) [](https://vscode.dev/redirect?url=vscode:mcp/install?%7B%22name%22%3A%22cyanheads-mcp-server%22%2C%22command%22%3A%22npx%22%2C%22args%22%3A%5B%22-y%22%2C%22%40cyanheads
|
|
16
|
+
[](https://github.com/cyanheads/cyanheads-mcp-server/releases/latest/download/cyanheads-mcp-server.mcpb) [](https://cursor.com/en/install-mcp?name=cyanheads-mcp-server&config=eyJjb21tYW5kIjoibnB4IiwiYXJncyI6WyIteSIsIkBjeWFuaGVhZHMvY3lhbmhlYWRzLW1jcC1zZXJ2ZXIiXX0=) [](https://vscode.dev/redirect?url=vscode:mcp/install?%7B%22name%22%3A%22cyanheads-mcp-server%22%2C%22command%22%3A%22npx%22%2C%22args%22%3A%5B%22-y%22%2C%22%40cyanheads%2Fcyanheads-mcp-server%22%5D%7D)
|
|
17
17
|
|
|
18
18
|
[](https://www.npmjs.com/package/@cyanheads/mcp-ts-core)
|
|
19
19
|
|
|
@@ -27,65 +27,53 @@
|
|
|
27
27
|
|
|
28
28
|
---
|
|
29
29
|
|
|
30
|
-
##
|
|
30
|
+
## Overview
|
|
31
31
|
|
|
32
|
-
|
|
32
|
+
Fleet discovery for the cyanheads MCP ecosystem, built on a hosted `fleet.json` catalog of pre-computed tool and server embeddings. Search the catalog by natural-language query, or resolve a known tool or server name to its description, connection URL, and per-client install snippet. Runs as a stdio process, a local Streamable HTTP server, or the public hosted endpoint above.
|
|
33
|
+
|
|
34
|
+
### Tools
|
|
33
35
|
|
|
34
36
|
| Tool | Description |
|
|
35
37
|
|:---|:---|
|
|
36
38
|
| `cyanheads_search_catalog` | Search fleet tools and servers by natural-language query. Returns ranked matches with brief summaries and the owning server. |
|
|
37
|
-
| `cyanheads_describe_entry` | Return the connection URL and per-client install
|
|
39
|
+
| `cyanheads_describe_entry` | Return the description, connection URL, and per-client install snippet for a named tool or server. |
|
|
38
40
|
|
|
39
|
-
|
|
41
|
+
## Capability reference
|
|
40
42
|
|
|
41
|
-
|
|
43
|
+
### `cyanheads_search_catalog` <sub>tool</sub>
|
|
42
44
|
|
|
43
|
-
- `query`
|
|
44
|
-
- `
|
|
45
|
-
- `
|
|
46
|
-
-
|
|
47
|
-
- Returns `score` (cosine similarity in [0, 1]) on every result for trust calibration
|
|
48
|
-
- `totalCount` reports the count above the floor before the limit was applied
|
|
45
|
+
- `query` 1–500 raw characters, with non-whitespace text required; surrounding whitespace is trimmed before embedding and echo. `scope` selects `tools` (default) or `servers`; optional `category`: `research`, `government`, `public-data`, `utility`; `limit` 1–20 (default 5).
|
|
46
|
+
- Results carry cosine-similarity `score` (`[0, 1]`, comparable within one response). Tool searches include a `servers` roll-up with ten entries per page and `serversTotal`; an unloaded catalog returns retryable `catalog_empty`.
|
|
47
|
+
- Page results with `offset` and the tools-scope roll-up independently with `serversOffset` (both default to 0). Reuse the same query, scope, category, and limit with `nextOffset` / `nextServersOffset`; null means exhausted. Each call uses the current catalog, so a refresh between pages can change ordering. Servers scope requires `serversOffset: 0` and omits roll-up fields.
|
|
48
|
+
- `SIMILARITY_FLOOR` (default `0.3`) filters matches before the limit applies.
|
|
49
49
|
|
|
50
50
|
---
|
|
51
51
|
|
|
52
|
-
### `cyanheads_describe_entry`
|
|
53
|
-
|
|
54
|
-
Resolve a name to its install instructions. Accepts either a tool name (snake_case, e.g. `earthquake_search`) or a server name (kebab-case, e.g. `earthquake-mcp-server`), up to 64 characters — auto-detected from the format, or pinned via the `kind` parameter.
|
|
52
|
+
### `cyanheads_describe_entry` <sub>tool</sub>
|
|
55
53
|
|
|
56
|
-
-
|
|
57
|
-
-
|
|
58
|
-
-
|
|
59
|
-
-
|
|
60
|
-
- Discriminated output on `kind` — callers branch on data, not string parsing
|
|
54
|
+
- `name` 1–64 characters accepts a tool or server name, auto-detected or pinned via `kind`. Exact names win, then unique case-insensitive names; output uses canonical names. `client` optionally selects `claude-code`, `codex`, `cursor`, `gemini`, `streamable-http`, or `curl`.
|
|
55
|
+
- Both kinds return connection metadata and install snippets; server results also include the full tool inventory. Published servers get local snippets; hosted servers also get HTTP snippets. For local-only entries, `client: "curl"` returns successful metadata with an `installNotice` naming a stdio client to try. Required environment variables remain visible even without snippets.
|
|
56
|
+
- Descriptions are catalog text; obtain tool schemas from the connected server's `tools/list`.
|
|
57
|
+
- Failures return `not_found`, `ambiguous_kind` (set `kind`), or retryable `catalog_empty`.
|
|
61
58
|
|
|
62
59
|
## Features
|
|
63
60
|
|
|
64
|
-
Built on [`@cyanheads/mcp-ts-core`](https://github.com/cyanheads/mcp-ts-core):
|
|
65
|
-
|
|
66
|
-
- Declarative tool definitions — single file per tool, framework handles registration and validation
|
|
67
|
-
- Unified error handling with typed error contracts and recovery hints
|
|
68
|
-
- Pluggable auth (`none`, `jwt`, `oauth`)
|
|
69
|
-
- Structured logging with optional OpenTelemetry tracing
|
|
70
|
-
- Runs locally over stdio or HTTP, with a hosted Streamable HTTP endpoint
|
|
71
|
-
|
|
72
|
-
Fleet-specific:
|
|
61
|
+
Built on [`@cyanheads/mcp-ts-core`](https://github.com/cyanheads/mcp-ts-core): stdio and Streamable HTTP transports, pluggable auth (`none` / `jwt` / `oauth`), swappable storage (`in-memory`, `filesystem`, `Supabase`, `Cloudflare KV/R2/D1`), structured logging with optional OpenTelemetry tracing.
|
|
73
62
|
|
|
74
|
-
-
|
|
75
|
-
- L2-normalized 256-dim Matryoshka-truncated vectors keep memory under 100KB for a 40-server fleet
|
|
76
|
-
- Per-client install snippet generation at describe-time, not catalog-generation time — both local (stdio `npx`) and remote (Streamable HTTP) transports, kept in sync with the deployed endpoint
|
|
77
|
-
- Discriminated `result.kind` and typed `installSnippets[].client` / `installSnippets[].transport` enums — agents can branch reliably
|
|
63
|
+
Catalog-specific:
|
|
78
64
|
|
|
79
|
-
|
|
65
|
+
- Hourly background catalog refresh (`CATALOG_REFRESH_SECONDS`, default `3600`) with an atomic index swap when `generatedAt` changes — no restart needed
|
|
66
|
+
- Empty catalogs and conflicting duplicate identities fail before index replacement; refresh retains the last valid catalog. Identical duplicates collapse before indexing, with a bounded load-time warning; servers with no tools remain valid.
|
|
67
|
+
- Query embeddings are computed at request time via `@huggingface/transformers`; document embeddings are pre-computed, L2-normalized, and Matryoshka-truncated, shipped inside `fleet.json`
|
|
68
|
+
- The embedding model is warmed up during startup, before OpenTelemetry's HTTP instrumentation patches `fetch` — avoids a cold-cache model-load failure under OTEL
|
|
69
|
+
- Self-describing: `cyanheads_describe_entry` resolves this server's own name and tools from a static fallback record, consulted only when the remote catalog doesn't carry an entry for it
|
|
70
|
+
- `CATALOG_URL` can point at any endpoint serving the same schema, to front a custom fleet
|
|
80
71
|
|
|
81
|
-
|
|
72
|
+
Agent-friendly output:
|
|
82
73
|
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
| **Government** | OpenStates, USAspending, CourtListener, NIST NVD, Library of Congress |
|
|
87
|
-
| **Public Data** | Earthquake (USGS), NOAA Weather, GBIF Biodiversity, World Bank, WHO, Eurostat |
|
|
88
|
-
| **Utility** | OpenStreetMap geocoding, Reference Data (constants, timezones, units), WSDOT |
|
|
74
|
+
- Search responses echo the effective query, report the total match count before the limit, and include broadening guidance when nothing matches
|
|
75
|
+
- Discriminated `result.kind` (`tool` | `server`) on `cyanheads_describe_entry` lets callers branch on data, not string parsing
|
|
76
|
+
- Every search result carries a `score` field for trust calibration, plus a `servers` roll-up so agents can see which servers matched without a second call
|
|
89
77
|
|
|
90
78
|
## Getting started
|
|
91
79
|
|
|
@@ -171,7 +159,7 @@ MCP_TRANSPORT_TYPE=http MCP_HTTP_PORT=3010 bun run start:http
|
|
|
171
159
|
|
|
172
160
|
### Prerequisites
|
|
173
161
|
|
|
174
|
-
- [Bun v1.
|
|
162
|
+
- [Bun v1.4.0](https://bun.sh/) or higher (or Node.js v24+).
|
|
175
163
|
|
|
176
164
|
### Installation
|
|
177
165
|
|
|
@@ -193,6 +181,13 @@ cd cyanheads-mcp-server
|
|
|
193
181
|
bun install
|
|
194
182
|
```
|
|
195
183
|
|
|
184
|
+
4. **Configure environment:**
|
|
185
|
+
|
|
186
|
+
```sh
|
|
187
|
+
cp .env.example .env
|
|
188
|
+
# edit .env to override any defaults
|
|
189
|
+
```
|
|
190
|
+
|
|
196
191
|
## Configuration
|
|
197
192
|
|
|
198
193
|
All configuration is validated at startup via Zod schemas in `src/config/server-config.ts`. Every variable has a sensible default — out of the box, the server points at the canonical cyanheads fleet.
|
|
@@ -204,6 +199,7 @@ All configuration is validated at startup via Zod schemas in `src/config/server-
|
|
|
204
199
|
| `MCP_HTTP_HOST` | HTTP server bind host | `127.0.0.1` |
|
|
205
200
|
| `MCP_HTTP_ENDPOINT_PATH` | HTTP endpoint path where the MCP server is mounted | `/mcp` |
|
|
206
201
|
| `MCP_AUTH_MODE` | Authentication: `none`, `jwt`, or `oauth` | `none` |
|
|
202
|
+
| `MCP_SESSION_MODE` | HTTP session posture: `auto`, `stateful`, or `stateless`. `src/index.ts` declares `stateless`; set this only to override it. | `stateless` |
|
|
207
203
|
| `MCP_LOG_LEVEL` | Log level (`debug`, `info`, `warning`, `error`, etc.) | `info` |
|
|
208
204
|
| `CATALOG_URL` | Remote fleet.json endpoint (schema v2 with baked embeddings). Must be an absolute URL. Override to front your own fleet. | `https://caseyjhand.com/fleet.json` |
|
|
209
205
|
| `CATALOG_FETCH_TIMEOUT_MS` | Per-request timeout for fleet.json fetches in ms. Must be > 0. | `10000` |
|
|
@@ -211,14 +207,18 @@ All configuration is validated at startup via Zod schemas in `src/config/server-
|
|
|
211
207
|
| `EMBEDDING_MODEL_ID` | Hugging Face model id for query embedding. Must match `fleet.json.embeddingModel`. | `Snowflake/snowflake-arctic-embed-m-v1.5` |
|
|
212
208
|
| `SIMILARITY_FLOOR` | Cosine similarity cutoff for `cyanheads_search_catalog` results. Must be within `[0, 1]`. | `0.3` |
|
|
213
209
|
| `OTEL_ENABLED` | Enable OpenTelemetry | `false` |
|
|
210
|
+
| `OTEL_EXPORTER_OTLP_ENDPOINT` | OTLP base URL for traces and metrics | Unset |
|
|
211
|
+
| `OTEL_EXPORTER_OTLP_LOGS_ENDPOINT` | Explicit OTLP logs URL; requires the OTel log peers included in the default Docker build | Unset |
|
|
212
|
+
| `LOG_TOOL_FAILURE_PAYLOADS` | Log failed arguments and results, redacted by key name. Secrets inside free-form values are not redacted. | `false` |
|
|
213
|
+
| `LOG_TOOL_FAILURE_PAYLOAD_MAX_BYTES` | UTF-8 byte cap for each logged failure payload | `16384` |
|
|
214
214
|
|
|
215
|
-
|
|
215
|
+
See [`.env.example`](./.env.example) for the full list of optional overrides.
|
|
216
216
|
|
|
217
217
|
## Running the server
|
|
218
218
|
|
|
219
219
|
### Local development
|
|
220
220
|
|
|
221
|
-
- **Build and run the production version
|
|
221
|
+
- **Build and run the production version:**
|
|
222
222
|
|
|
223
223
|
```sh
|
|
224
224
|
# One-time build
|
|
@@ -230,12 +230,22 @@ To point at a different catalog, change `CATALOG_URL` to your own hosted JSON fi
|
|
|
230
230
|
bun run start:stdio
|
|
231
231
|
```
|
|
232
232
|
|
|
233
|
-
- **Run checks and tests
|
|
233
|
+
- **Run checks and tests:**
|
|
234
|
+
|
|
234
235
|
```sh
|
|
235
236
|
bun run devcheck # Lints, formats, type-checks, runs MCP and packaging linters
|
|
236
237
|
bun run test # Runs the test suite
|
|
237
238
|
```
|
|
238
239
|
|
|
240
|
+
### Docker
|
|
241
|
+
|
|
242
|
+
```sh
|
|
243
|
+
docker build -t cyanheads-mcp-server .
|
|
244
|
+
docker run --rm -p 3010:3010 cyanheads-mcp-server
|
|
245
|
+
```
|
|
246
|
+
|
|
247
|
+
The Dockerfile defaults to HTTP transport, stateless session mode, and logs to `/var/log/cyanheads-mcp-server`. OpenTelemetry peer dependencies are installed by default — build with `--build-arg OTEL_ENABLED=false` to omit them.
|
|
248
|
+
|
|
239
249
|
## Project structure
|
|
240
250
|
|
|
241
251
|
| Directory | Purpose |
|
|
@@ -253,10 +263,11 @@ See [`CLAUDE.md`](./CLAUDE.md) for development guidelines and architectural rule
|
|
|
253
263
|
- Handlers throw, framework catches — no `try/catch` in tool logic
|
|
254
264
|
- Use `ctx.log` for logging, `ctx.state` for storage
|
|
255
265
|
- Register new tools in the `tools` array passed to `createApp()` in `src/index.ts`
|
|
266
|
+
- Wrap external data: validate raw → normalize to domain type → return output schema; never fabricate missing fields
|
|
256
267
|
|
|
257
268
|
## Contributing
|
|
258
269
|
|
|
259
|
-
Issues
|
|
270
|
+
Issues are welcome. Run checks and tests before submitting:
|
|
260
271
|
|
|
261
272
|
```sh
|
|
262
273
|
bun run devcheck
|
|
@@ -265,4 +276,4 @@ bun run test
|
|
|
265
276
|
|
|
266
277
|
## License
|
|
267
278
|
|
|
268
|
-
|
|
279
|
+
Apache-2.0 — see [LICENSE](LICENSE) for details.
|
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
---
|
|
2
|
+
summary: "Adopts mcp-ts-core 0.13's session-mode API and InvalidParams argument-rejection envelope; MCP_SESSION_MODE now defaults to stateless everywhere, and catalog_empty errors correctly advertise retryable."
|
|
3
|
+
breaking: false
|
|
4
|
+
security: false
|
|
5
|
+
---
|
|
6
|
+
|
|
7
|
+
# 0.4.2 — 2026-09-19
|
|
8
|
+
|
|
9
|
+
## Changed
|
|
10
|
+
|
|
11
|
+
- **`@cyanheads/mcp-ts-core` `^0.12.3` → `^0.13.6`** adopts `createApp({ sessionMode, teardown })`, moves the framework's skill tree to `framework-skills/`, and tightens the tool-argument rejection envelope.
|
|
12
|
+
- **`MCP_SESSION_MODE` defaults to `stateless`** (#18) via `createApp({ sessionMode: 'stateless' })` in `src/index.ts`, so the container, `bunx`, and a source run all agree — previously only the Docker image defaulted to it.
|
|
13
|
+
- **Tool argument rejections classify as `InvalidParams` (`-32602`)**, not `ValidationError` (`-32007`), and `content[]` now closes with a schema-derived `Recovery:` hint and a `(reason … )` trailer.
|
|
14
|
+
- **The server card publishes the resolved session mode** under the namespaced `_meta` key `io.github.cyanheads.mcp-ts-core/sessionMode`.
|
|
15
|
+
|
|
16
|
+
## Fixed
|
|
17
|
+
|
|
18
|
+
- **`catalog_empty` now advertises `retryable: true` on the wire** (#19) — both throw sites (`CatalogService._assertInitialized`, `getCatalogService`) set it, so the `content[]` trailer agrees with what both tools declare in `errors[]`.
|
|
19
|
+
|
|
20
|
+
## Dependencies
|
|
21
|
+
|
|
22
|
+
- `@cyanheads/mcp-ts-core` ^0.12.3 → ^0.13.6
|
|
23
|
+
- `zod` ^4.4.3 → ^4.6.5
|
|
24
|
+
- `@huggingface/transformers` 4.2.0 → 4.3.0
|
|
25
|
+
- `@biomejs/biome` ^2.5.9 → ^2.5.14 (dev)
|
|
26
|
+
- `@types/node` ^26.2.0 → ^26.6.1 (dev)
|
|
27
|
+
- `vitest` ^4.1.11 → ^5.0.1 (dev)
|
|
28
|
+
- `@vitest/coverage-istanbul` 4.1.11 → 5.0.1 (dev)
|
|
29
|
+
- `fast-check` 4.9.0 → 4.10.1 (dev)
|
|
30
|
+
- `ignore` ^7.0.6 → ^7.0.9 (dev)
|
|
31
|
+
- `tsc-alias` ^1.9.2 → ^1.9.5 (dev)
|
|
32
|
+
- Bun engine `>=1.3.0` → `>=1.4.0`
|
|
@@ -0,0 +1,34 @@
|
|
|
1
|
+
---
|
|
2
|
+
summary: "Catalog integrity fixes, complete search pagination, and client-specific installation guidance for every entry."
|
|
3
|
+
breaking: false
|
|
4
|
+
security: false
|
|
5
|
+
---
|
|
6
|
+
|
|
7
|
+
# 0.4.3 — 2026-09-30
|
|
8
|
+
|
|
9
|
+
## Changed
|
|
10
|
+
|
|
11
|
+
- **Docker builds** install target-platform dependencies on the native builder with Bun `1.4.0 → 1.4.2`; OpenTelemetry peers use the framework's tested ranges, security scanner, and release-age policy. Runtime logging follows framework configuration.
|
|
12
|
+
- **Development tooling** synchronizes framework skills and checks for definition import failures, bundle/version alignment, Docker build platforms, skill versions, and release annotations. Publishing uses a gated release PR.
|
|
13
|
+
- **Documentation and packaging** describe current catalog behavior, failure-payload logging, and OTLP logs configuration; correct the VS Code install link and exclude runtime logs and nested bundles from distribution artifacts.
|
|
14
|
+
|
|
15
|
+
## Fixed
|
|
16
|
+
|
|
17
|
+
- **Search queries** reject whitespace-only input before embedding and trim valid queries for embedding and echo, retaining the 500-character raw limit. ([#12](https://github.com/cyanheads/cyanheads-mcp-server/issues/12))
|
|
18
|
+
- **Search continuation** exposes independent result and server roll-up offsets, full totals, and nullable next offsets. Reuse the query and filters; pages reflect the current catalog. ([#13](https://github.com/cyanheads/cyanheads-mcp-server/issues/13))
|
|
19
|
+
- **Catalog normalization** collapses identical exact-name duplicates before indexing and rejects conflicting records; search, descriptions, counts, and vectors share the normalized inventory. ([#14](https://github.com/cyanheads/cyanheads-mcp-server/issues/14))
|
|
20
|
+
- **Literal rendering** preserves descriptions, identifiers, metadata, and install payloads through Markdown rendering with delimiter-sized code spans and blocks. ([#15](https://github.com/cyanheads/cyanheads-mcp-server/issues/15))
|
|
21
|
+
- **Tool installation handoffs** include owning-server connection metadata and client-filtered snippets. Local-only curl requests return actionable stdio guidance, with required environment variables visible even when no snippet applies. ([#16](https://github.com/cyanheads/cyanheads-mcp-server/issues/16))
|
|
22
|
+
- **Empty catalogs** fail startup validation and retain the previous index on refresh; nonempty catalogs with zero-tool servers remain valid. ([#17](https://github.com/cyanheads/cyanheads-mcp-server/issues/17))
|
|
23
|
+
- **Name resolution** prefers exact remote names, then unique case-insensitive matches, and returns canonical names. Ambiguous folds remain unresolved; remote entries take precedence over self records. ([#20](https://github.com/cyanheads/cyanheads-mcp-server/issues/20))
|
|
24
|
+
- **Error recovery** uses framework-populated contract hints for handler and service failures, including retryable `catalog_empty` responses.
|
|
25
|
+
|
|
26
|
+
## Dependencies
|
|
27
|
+
|
|
28
|
+
- `@cyanheads/mcp-ts-core` `^0.13.6 → ^0.13.10`.
|
|
29
|
+
- `@socketsecurity/bun-security-scanner` `^1.1.2 → ^1.1.3`.
|
|
30
|
+
- `@types/node` `^26.6.1 → ^26.6.3`.
|
|
31
|
+
- `@vitest/coverage-istanbul` `5.0.1 → 5.0.2`.
|
|
32
|
+
- `fast-check` `4.10.1 → 4.10.2`.
|
|
33
|
+
- `ignore` `^7.0.9 → ^7.0.10`.
|
|
34
|
+
- `vitest` `^5.0.1 → ^5.0.2`.
|
package/changelog/template.md
CHANGED
|
@@ -6,8 +6,8 @@
|
|
|
6
6
|
|
|
7
7
|
# Required. One-line GitHub Release-style headline. 350 character cap — a
|
|
8
8
|
# ceiling, not a target. Default short and scannable. Don't pad, don't stitch
|
|
9
|
-
# unrelated changes with commas/semicolons into an inventory — pick the
|
|
10
|
-
# headline
|
|
9
|
+
# unrelated changes with commas/semicolons into an inventory — pick the one
|
|
10
|
+
# headline the release is about. Quotes required: unquoted YAML treats
|
|
11
11
|
# `: ` inside the value as a key separator and fails GitHub's strict parser.
|
|
12
12
|
summary: ""
|
|
13
13
|
|
|
@@ -117,30 +117,13 @@ security: false
|
|
|
117
117
|
in that unrelated item's metadata.
|
|
118
118
|
|
|
119
119
|
TAG ANNOTATIONS — the annotated tag body renders as the GitHub Release body
|
|
120
|
-
via `gh release create --notes-from-tag`.
|
|
121
|
-
|
|
122
|
-
|
|
123
|
-
|
|
124
|
-
|
|
125
|
-
|
|
126
|
-
|
|
127
|
-
Dependency bumps: ← section header
|
|
128
|
-
← blank line
|
|
129
|
-
- `@cyanheads/mcp-ts-core` ^0.9.1 → ^0.9.6 ← bullet
|
|
130
|
-
← blank line
|
|
131
|
-
Changed: ← only sections with entries
|
|
132
|
-
← blank line
|
|
133
|
-
- `format()` output includes `query` in text mode
|
|
134
|
-
← blank line
|
|
135
|
-
Added:
|
|
136
|
-
← blank line
|
|
137
|
-
- `manifest.json` scaffolded for MCPB bundle support
|
|
138
|
-
- Install badges (Claude Desktop, Cursor, VS Code)
|
|
139
|
-
← blank line
|
|
140
|
-
<N> tests pass; `bun run devcheck` clean. ← footer
|
|
141
|
-
|
|
142
|
-
Never a flat comma-separated string. Always structured markdown with
|
|
143
|
-
sections. The tag must scan well as a rendered GitHub Release page.
|
|
120
|
+
via `gh release create --notes-from-tag`. It is a condensed digest of this
|
|
121
|
+
entry, never a copy, and its format is owned by the `release-and-publish`
|
|
122
|
+
skill (step 4, "Create the annotated tag"): a short subject line without the
|
|
123
|
+
version, flat headline bullets — no Keep-a-Changelog section headers, no
|
|
124
|
+
gates line — at most one deps line, issue backlinks, and the changelog link
|
|
125
|
+
last. In release-PR mode the `git-wrapup` skill authors those bullets as the
|
|
126
|
+
PR body's `## Changes` and the tag copies them.
|
|
144
127
|
-->
|
|
145
128
|
|
|
146
129
|
## Added
|
package/dist/index.js
CHANGED
|
@@ -12,12 +12,24 @@ import { getCatalogService } from './services/catalog/service-instance.js';
|
|
|
12
12
|
await createApp({
|
|
13
13
|
name: 'cyanheads-mcp-server',
|
|
14
14
|
title: 'cyanheads-mcp-server',
|
|
15
|
+
/**
|
|
16
|
+
* No per-session state: the catalog index is process-wide and `ctx.state` is
|
|
17
|
+
* tenant-scoped, so the session store and the per-session `McpServer` buy
|
|
18
|
+
* nothing here and cost horizontal scalability. `MCP_SESSION_MODE` still wins
|
|
19
|
+
* when a deployment sets it to a meaningful value; the Dockerfile's
|
|
20
|
+
* `ENV MCP_SESSION_MODE="stateless"` now restates this rather than overriding
|
|
21
|
+
* a different default. No tool calls `ctx.requestInput`, so `require` is not
|
|
22
|
+
* declared — nothing here degrades under stateless.
|
|
23
|
+
*/
|
|
24
|
+
sessionMode: 'stateless',
|
|
15
25
|
tools: [searchCatalogTool, describeEntryTool],
|
|
16
26
|
resources: [],
|
|
17
27
|
prompts: [],
|
|
18
28
|
instructions: 'This server is the discovery front door to the cyanheads MCP fleet. ' +
|
|
19
29
|
'Use cyanheads_search_catalog to find tools or servers by describing what you want to do. ' +
|
|
20
|
-
'Use cyanheads_describe_entry to get
|
|
30
|
+
'Use cyanheads_describe_entry to get descriptions, connection metadata, and per-client install snippets for any result. ' +
|
|
31
|
+
'Tool schemas are available from the connected server through tools/list. ' +
|
|
32
|
+
'Continue searches with nextOffset and, in tools scope, nextServersOffset; reuse the same query and filters. ' +
|
|
21
33
|
'Scope "tools" (default) finds individual tools; scope "servers" finds which server owns a workflow. ' +
|
|
22
34
|
'cyanheads_describe_entry also resolves this server itself, under the name "cyanheads-mcp-server".',
|
|
23
35
|
async setup() {
|
|
@@ -25,5 +37,14 @@ await createApp({
|
|
|
25
37
|
initCatalogService(config);
|
|
26
38
|
await getCatalogService().initialize();
|
|
27
39
|
},
|
|
40
|
+
/**
|
|
41
|
+
* `setup()` arms a ref'd `setInterval` for the background catalog refresh.
|
|
42
|
+
* Nothing else clears it, so without this hook a signal shutdown cuts the
|
|
43
|
+
* timer rather than releasing it. Runs after the transport stops accepting
|
|
44
|
+
* requests and before core services are disposed.
|
|
45
|
+
*/
|
|
46
|
+
teardown() {
|
|
47
|
+
getCatalogService().shutdown();
|
|
48
|
+
},
|
|
28
49
|
});
|
|
29
50
|
//# sourceMappingURL=index.js.map
|
package/dist/index.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":";AACA;;;GAGG;AAEH,OAAO,EAAE,SAAS,EAAE,MAAM,wBAAwB,CAAC;AACnD,OAAO,EAAE,eAAe,EAAE,MAAM,2BAA2B,CAAC;AAC5D,OAAO,EAAE,iBAAiB,EAAE,MAAM,uDAAuD,CAAC;AAC1F,OAAO,EAAE,iBAAiB,EAAE,MAAM,uDAAuD,CAAC;AAC1F,OAAO,EAAE,kBAAkB,EAAE,MAAM,uCAAuC,CAAC;AAC3E,OAAO,EAAE,iBAAiB,EAAE,MAAM,wCAAwC,CAAC;AAE3E,MAAM,SAAS,CAAC;IACd,IAAI,EAAE,sBAAsB;IAC5B,KAAK,EAAE,sBAAsB;IAC7B,KAAK,EAAE,CAAC,iBAAiB,EAAE,iBAAiB,CAAC;IAC7C,SAAS,EAAE,EAAE;IACb,OAAO,EAAE,EAAE;IACX,YAAY,EACV,sEAAsE;QACtE,2FAA2F;QAC3F,
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":";AACA;;;GAGG;AAEH,OAAO,EAAE,SAAS,EAAE,MAAM,wBAAwB,CAAC;AACnD,OAAO,EAAE,eAAe,EAAE,MAAM,2BAA2B,CAAC;AAC5D,OAAO,EAAE,iBAAiB,EAAE,MAAM,uDAAuD,CAAC;AAC1F,OAAO,EAAE,iBAAiB,EAAE,MAAM,uDAAuD,CAAC;AAC1F,OAAO,EAAE,kBAAkB,EAAE,MAAM,uCAAuC,CAAC;AAC3E,OAAO,EAAE,iBAAiB,EAAE,MAAM,wCAAwC,CAAC;AAE3E,MAAM,SAAS,CAAC;IACd,IAAI,EAAE,sBAAsB;IAC5B,KAAK,EAAE,sBAAsB;IAC7B;;;;;;;;OAQG;IACH,WAAW,EAAE,WAAW;IACxB,KAAK,EAAE,CAAC,iBAAiB,EAAE,iBAAiB,CAAC;IAC7C,SAAS,EAAE,EAAE;IACb,OAAO,EAAE,EAAE;IACX,YAAY,EACV,sEAAsE;QACtE,2FAA2F;QAC3F,yHAAyH;QACzH,2EAA2E;QAC3E,8GAA8G;QAC9G,sGAAsG;QACtG,mGAAmG;IAErG,KAAK,CAAC,KAAK;QACT,MAAM,MAAM,GAAG,eAAe,EAAE,CAAC;QACjC,kBAAkB,CAAC,MAAM,CAAC,CAAC;QAC3B,MAAM,iBAAiB,EAAE,CAAC,UAAU,EAAE,CAAC;IACzC,CAAC;IAED;;;;;OAKG;IACH,QAAQ;QACN,iBAAiB,EAAE,CAAC,QAAQ,EAAE,CAAC;IACjC,CAAC;CACF,CAAC,CAAC"}
|
|
@@ -27,6 +27,28 @@ export declare const describeEntryTool: import("@cyanheads/mcp-ts-core").ToolDef
|
|
|
27
27
|
name: z.ZodString;
|
|
28
28
|
description: z.ZodString;
|
|
29
29
|
server: z.ZodString;
|
|
30
|
+
npm: z.ZodString;
|
|
31
|
+
github: z.ZodString;
|
|
32
|
+
endpoint: z.ZodOptional<z.ZodString>;
|
|
33
|
+
auth: z.ZodString;
|
|
34
|
+
requiredEnvVars: z.ZodOptional<z.ZodArray<z.ZodString>>;
|
|
35
|
+
installNotice: z.ZodOptional<z.ZodString>;
|
|
36
|
+
installSnippets: z.ZodArray<z.ZodObject<{
|
|
37
|
+
client: z.ZodEnum<{
|
|
38
|
+
"claude-code": "claude-code";
|
|
39
|
+
codex: "codex";
|
|
40
|
+
curl: "curl";
|
|
41
|
+
cursor: "cursor";
|
|
42
|
+
gemini: "gemini";
|
|
43
|
+
"streamable-http": "streamable-http";
|
|
44
|
+
}>;
|
|
45
|
+
transport: z.ZodEnum<{
|
|
46
|
+
http: "http";
|
|
47
|
+
stdio: "stdio";
|
|
48
|
+
}>;
|
|
49
|
+
label: z.ZodString;
|
|
50
|
+
payload: z.ZodString;
|
|
51
|
+
}, z.core.$strip>>;
|
|
30
52
|
}, z.core.$strip>, z.ZodObject<{
|
|
31
53
|
kind: z.ZodLiteral<"server">;
|
|
32
54
|
name: z.ZodString;
|
|
@@ -38,6 +60,7 @@ export declare const describeEntryTool: import("@cyanheads/mcp-ts-core").ToolDef
|
|
|
38
60
|
endpoint: z.ZodOptional<z.ZodString>;
|
|
39
61
|
auth: z.ZodString;
|
|
40
62
|
requiredEnvVars: z.ZodOptional<z.ZodArray<z.ZodString>>;
|
|
63
|
+
installNotice: z.ZodOptional<z.ZodString>;
|
|
41
64
|
toolCount: z.ZodNumber;
|
|
42
65
|
tools: z.ZodArray<z.ZodObject<{
|
|
43
66
|
name: z.ZodString;
|
|
@@ -76,5 +99,6 @@ export declare const describeEntryTool: import("@cyanheads/mcp-ts-core").ToolDef
|
|
|
76
99
|
readonly when: "Catalog has not finished loading.";
|
|
77
100
|
readonly recovery: "Retry in a few seconds; the catalog is still loading.";
|
|
78
101
|
readonly retryable: true;
|
|
102
|
+
readonly thrownBy: "service";
|
|
79
103
|
}], undefined>;
|
|
80
104
|
//# sourceMappingURL=describe-entry.tool.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"describe-entry.tool.d.ts","sourceRoot":"","sources":["../../../../src/mcp-server/tools/definitions/describe-entry.tool.ts"],"names":[],"mappings":"AAAA;;;;;;GAMG;AAEH,OAAO,EAAQ,CAAC,EAAE,MAAM,wBAAwB,CAAC;AACjD,OAAO,EAAE,gBAAgB,EAAE,MAAM,+BAA+B,CAAC;
|
|
1
|
+
{"version":3,"file":"describe-entry.tool.d.ts","sourceRoot":"","sources":["../../../../src/mcp-server/tools/definitions/describe-entry.tool.ts"],"names":[],"mappings":"AAAA;;;;;;GAMG;AAEH,OAAO,EAAQ,CAAC,EAAE,MAAM,wBAAwB,CAAC;AACjD,OAAO,EAAE,gBAAgB,EAAE,MAAM,+BAA+B,CAAC;AAajE,eAAO,MAAM,iBAAiB;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;cAqT5B,CAAC"}
|