Skip to content

Commit 3ca86bc

Browse files
authored
Merge pull request #14 from Litenova-Solutions/feature/mcp-install
feat: add `fuse mcp install` and group the MCP surface under `fuse mcp`
2 parents 65e66a0 + 3120963 commit 3ca86bc

36 files changed

Lines changed: 1132 additions & 61 deletions

.editorconfig

Lines changed: 31 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,31 @@
1+
root = true
2+
3+
# All files
4+
[*]
5+
charset = utf-8
6+
insert_final_newline = true
7+
trim_trailing_whitespace = true
8+
9+
# C# source files
10+
[*.{cs,csx}]
11+
indent_size = 4
12+
indent_style = space
13+
tab_width = 4
14+
15+
[*.cs]
16+
# One type (class, struct, interface, enum, or delegate) per file.
17+
# Enforced by convention; split types into separate files named after the type.
18+
19+
# Match existing Fuse style.
20+
csharp_style_namespace_declarations = file_scoped:suggestion
21+
22+
# Shell and web assets keep LF where pinned in .gitattributes.
23+
[*.{sh,mdx,md,yml,yaml,json}]
24+
end_of_line = lf
25+
26+
[*.{csproj,props,targets,slnx,xml,md,mdx,json,yml,yaml,html,css,tsx,ts,js}]
27+
indent_size = 2
28+
indent_style = space
29+
30+
[*.cs]
31+
indent_size = 4

AGENTS.md

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,7 @@ Read this before editing Fuse source or docs. It holds the durable context about
44

55
## What Fuse Is
66

7-
Fuse is a .NET-native codebase context optimizer for AI-assisted development. It collects source files, reduces them for token efficiency, and emits one structured payload an agent or developer can read in a single call instead of opening thousands of files. It ships as a .NET global tool (`fuse`) and as a Model Context Protocol server (`fuse serve`) with eight tools. It cuts tokens while keeping the public API intact, scopes to the files a task needs, and trims the round-trips an agent makes during its explore phase.
7+
Fuse is a .NET-native codebase context optimizer for AI-assisted development. It collects source files, reduces them for token efficiency, and emits one structured payload an agent or developer can read in a single call instead of opening thousands of files. It ships as a .NET global tool (`fuse`) and as a Model Context Protocol server (`fuse mcp serve`) with eight tools. It cuts tokens while keeping the public API intact, scopes to the files a task needs, and trims the round-trips an agent makes during its explore phase.
88

99
## Repository Layout
1010

CHANGELOG.md

Lines changed: 29 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,35 @@
22

33
All notable changes to Fuse are documented here. The format is based on Keep a Changelog. Fuse 2.0 is a structural rewrite; backward compatibility with 1.x output is not a goal.
44

5+
## [2.2.0]
6+
7+
Registering Fuse with an AI client is now one command, and the MCP surface is grouped under `fuse mcp`. The change is about setup ergonomics; the reduction, scoping, and emission paths are unchanged.
8+
9+
### Breaking changes
10+
11+
- **`fuse serve` moved to `fuse mcp serve`.** The stdio MCP server (the long-running process your client launches) is now a subcommand of the new `fuse mcp` group. Client configuration that launched `fuse serve` must change its arguments from `["serve"]` to `["mcp", "serve"]`. Re-running `fuse mcp install` rewrites them for you; for hand-written config, edit the `args` array. The MCP Registry manifest and the published package arguments are updated to match.
12+
13+
### Added
14+
15+
- **`fuse mcp install`**: registers Fuse as an MCP server with Claude Code, Cursor, or GitHub Copilot in one command, replacing per-tool JSON editing. `--client` targets one client or `all` (default); `--scope` writes project-local config (default, commit it so the team inherits Fuse) or user-global config (every project you open); `--command` overrides the launched executable. Claude Code user scope is registered through the Claude CLI; the other clients have their config file written directly. The installer merges into an existing config without dropping a co-located server's `env` or `cwd` block or top-level keys such as Copilot's `inputs` array, and it resolves the per-OS VS Code user profile directory rather than a path VS Code does not read.
16+
- **`fuse mcp` command group**: parents `install` and `serve`, separating the MCP server surface from the one-shot CLI.
17+
18+
## [2.1.0]
19+
20+
### Breaking changes
21+
22+
- **Single reduction level replaces the C# reduction flag cluster.** `--all`, `--skeleton`, `--public-api`, `--aggressive`, and the `--remove-csharp-*` switches are removed in favor of one `--level` option (and a matching `level` MCP parameter) with the values `none`, `standard`, `aggressive`, `skeleton`, and `publicApi`. The CLI commands default to `none`; the scoped MCP tools (`fuse_focus`, `fuse_search`, `fuse_changes`, `fuse_dotnet`) default to `standard`, so an agent gets the standard removals (which preserve 99 to 100 percent of the public API surface on the benchmark corpus) without naming a level. Migrate `--all` to `--level aggressive` (add `--collapse-generated` if you relied on `--all` collapsing generated code), `--aggressive` to `--level aggressive`, `--skeleton` to `--level skeleton`, `--public-api` to `--level publicApi`, and any `--remove-csharp-*` flag to `--level standard`. Redaction, generated-code collapse, semantic markers, pattern summary, route map, project graph, and minification stay orthogonal to the level.
23+
24+
### Added
25+
26+
- **Opt-in local embedding model for hybrid rerank** (`FUSE_EMBEDDINGS`): the `--rerank` vector path can use a real local ONNX embedding model, realizing the `IEmbeddingModel` plug point that shipped in 2.0 behind a deterministic lexical fallback. The model assembly is excluded from the Native AOT package, matching the isolation of the Roslyn precision tier, so the default AOT binary stays reflection-free.
27+
- **Chunk-granular query retrieval.** A `SymbolChunk` model and member-level chunk extractors let query scoping rank and pack at member granularity rather than whole files, feeding a thin-skeleton packing path that keeps the matched members in full while reducing the rest. Member selection is decoupled from file ranking so that packing at the member level does not lower file recall.
28+
- **Reduction-aware single-pass packing.** Packing fits content to a token budget in one pass with reduction accounted for, instead of reducing and then re-fitting.
29+
- **Near-duplicate member-body deduplication.** Members whose bodies are near-identical are collapsed, so repeated boilerplate bodies cost their tokens once.
30+
- **Persistent BM25 body-tokenization cache.** Body tokenization for the relevance index is cached by content hash, so repeated scoped runs skip re-tokenizing unchanged files. This is separate from the persistent analysis index added in 2.0.
31+
- **Tokenizer calibration harness.** A harness and a gated accuracy test calibrate the estimating tokenizers (the Anthropic and Gemini estimators) against reference counts.
32+
- **Redaction fidelity reporting.** The redaction report distinguishes secrets found in code literals from those in configuration, so a run can show where redaction acted.
33+
534
## [2.0.0]
635

736
Fuse 2.0 replaces the monolithic 1.x engine with axis-based projects and adds a Roslyn precision tier, hybrid retrieval, survey and round-trip tools, and a reproducible benchmark suite. Every measured figure below comes from the benchmark harness over the pinned corpus, counted with `o200k_base`; see [the benchmarks page](https://fuse.codes/docs/project/benchmarks). The precision tier and the survey, round-trip, and retrieval-rerank features are opt-in and do not change the default reduction or scoping path, so the default Layer 1 reduction and fidelity and the Layer 2 recall and precision are stable across runs.

README.md

Lines changed: 17 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -81,21 +81,33 @@ from [Releases](https://github.com/Litenova-Solutions/Fuse/releases). Verify wit
8181

8282
## Connect your agent
8383

84-
Run `fuse serve` and connect from your client. For Claude Code, add `.mcp.json` to your project root:
84+
Register Fuse once; your AI client launches `fuse mcp serve` automatically when MCP is enabled:
85+
86+
```bash
87+
fuse mcp install
88+
```
89+
90+
That writes MCP config for Claude Code, Cursor, and GitHub Copilot in the current project.
91+
Use `fuse mcp install --scope user` to register Fuse for every project on this machine.
92+
Use `fuse mcp install --client cursor` to configure one client only.
93+
94+
Manual registration is also supported. For Claude Code, add `.mcp.json` to your project root:
8595

8696
```json
8797
{
8898
"mcpServers": {
8999
"fuse": {
90100
"type": "stdio",
91101
"command": "fuse",
92-
"args": ["serve"]
102+
"args": ["mcp", "serve"]
93103
}
94104
}
95105
}
96106
```
97107

98-
Or register it in one line: `claude mcp add fuse --scope project -- fuse serve`. Cursor uses `.cursor/mcp.json` and GitHub Copilot uses `.vscode/mcp.json`; see [Connect to your AI](https://fuse.codes/docs/start/connect-your-ai) for both.
108+
Or register with the Claude CLI: `claude mcp add fuse --scope project -- fuse mcp serve`
109+
(use `--scope user` for all projects). Cursor uses `.cursor/mcp.json` and GitHub Copilot
110+
uses `.vscode/mcp.json`; see [Connect to your AI](https://fuse.codes/docs/start/connect-your-ai) for both.
99111

100112
A recommended agent flow on a large codebase: survey with `fuse_toc` or `fuse_skeleton`, drill in with `fuse_focus` or `fuse_search`, then review a branch with `fuse_changes`. Or call `fuse_ask` with a task and a token budget and let Fuse pick the strategy. See [Context for an agent](https://fuse.codes/docs/scenarios/context-for-an-agent).
101113

@@ -138,7 +150,8 @@ Output defaults to `Documents/Fuse`; use `--output` and `--name` to control the
138150
| `fuse dotnet` | .NET projects: C# reduction, structural maps, dependency-aware scoping. |
139151
| `fuse wiki` | Azure DevOps wikis: Markdown only. |
140152
| `fuse init` | Create `fuse.json` in the current directory. |
141-
| `fuse serve` | Start the MCP server on stdio. |
153+
| `fuse mcp install` | Register Fuse with MCP clients (Claude Code, Cursor, Copilot). |
154+
| `fuse mcp serve` | MCP server entry point on stdio (launched by your client, not run manually). |
142155

143156
Full option lists: [Commands](https://fuse.codes/docs/reference/commands) and [Options](https://fuse.codes/docs/reference/options).
144157

mcp-registry/server.json

Lines changed: 6 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,7 @@
33
"name": "io.github.Litenova-Solutions/fuse",
44
"title": "Fuse",
55
"description": "Token-efficient .NET codebase context for AI coding agents: skeleton, scoping, change-aware fusion.",
6-
"version": "2.0.1",
6+
"version": "2.2.0",
77
"repository": {
88
"url": "https://github.com/Litenova-Solutions/Fuse",
99
"source": "github",
@@ -15,12 +15,16 @@
1515
"registryType": "nuget",
1616
"registryBaseUrl": "https://api.nuget.org/v3/index.json",
1717
"identifier": "Fuse",
18-
"version": "2.0.1",
18+
"version": "2.2.0",
1919
"runtimeHint": "dnx",
2020
"transport": {
2121
"type": "stdio"
2222
},
2323
"packageArguments": [
24+
{
25+
"type": "positional",
26+
"value": "mcp"
27+
},
2428
{
2529
"type": "positional",
2630
"value": "serve"

packaging/README.md

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -10,7 +10,7 @@ who do not have the .NET SDK and want a single self-contained binary.
1010
|---------|---------|-------------------|-------------|
1111
| NuGet (`dotnet tool install -g Fuse`) | `v*.*.*` tag | `.github/workflows/publish.yml` (`build/pack-aot.ps1`) | Trusted Publishing (OIDC) + `NUGET_USER` |
1212
| GitHub Release (installer, self-contained win-x64 zip, linux-x64 tarball, `SHA256SUMS.txt`) | `v*.*.*` tag | `.github/workflows/release.yml` | built-in `GITHUB_TOKEN` |
13-
| MCP Registry (`fuse serve` discovery) | `v*.*.*` tag | `.github/workflows/mcp-registry.yml` (`mcp-registry/server.json`) | GitHub OIDC, no secret |
13+
| MCP Registry (`fuse mcp serve` discovery) | `v*.*.*` tag | `.github/workflows/mcp-registry.yml` (`mcp-registry/server.json`) | GitHub OIDC, no secret |
1414
| Install scripts (`curl ... \| sh`, `irm ... \| iex`) | served from the site | `site/public/install.sh`, `site/public/install.ps1` (at fuse.codes) | none |
1515
| WinGet (`winget install Litenova.Fuse`) | manual PR | `packaging/winget/*` -> `microsoft/winget-pkgs` | none (PR review) |
1616

@@ -23,7 +23,7 @@ SDK or runtime. The install scripts download those same release assets.
2323
org; repository owner `Litenova-Solutions`, repository `Fuse`, workflow file
2424
`publish.yml`). Add a `NUGET_USER` repo secret holding the nuget.org account
2525
name that owns the policy. No long-lived `NUGET_API_KEY` is needed.
26-
2. Push a tag, for example `git tag v2.0.0 && git push origin v2.0.0`.
26+
2. Push a tag, for example `git tag v2.2.0 && git push origin v2.2.0`.
2727
3. The three tag workflows run: NuGet push, the GitHub Release with assets, and
2828
the MCP Registry publish. The MCP publish validates the NuGet package and the
2929
`mcp-name: io.github.Litenova-Solutions/fuse` marker in the packed README, so

site/content/docs/concepts/sessions-and-deltas.mdx

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -46,7 +46,7 @@ The second call pays only for the files the agent does not already have.
4646

4747
## Honest Note
4848

49-
Session state is per-session and held in memory in the running `fuse serve` process, which
49+
Session state is per-session and held in memory in the running `fuse mcp serve` process, which
5050
is the session boundary. It is never persisted, so it is lost when the server process
5151
exits, and resetting a session makes the next call resend everything. Session-delta is a
5252
property of the MCP server across a live agent conversation; a one-off CLI run does not

site/content/docs/index.mdx

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,7 @@ description: Fuse collapses an AI coding agent's explore phase on a .NET codebas
66
Fuse collapses an AI coding agent's explore phase into one scoped call: it finds the
77
code a task needs on a .NET codebase and hands it over already reduced, so the agent
88
starts work instead of opening thousands of files to find its way around. It ships as
9-
a Model Context Protocol server (`fuse serve`) with eight tools for an agent, and as a
9+
a Model Context Protocol server (`fuse mcp serve`) with eight tools for an agent, and as a
1010
.NET global tool (`fuse`) for the terminal and CI.
1111

1212
These docs are organized so you can read top to bottom to learn, or jump to a

site/content/docs/project/changelog.mdx

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -13,7 +13,9 @@ The repository CHANGELOG.md file documents every notable change by version, incl
1313

1414
## Most Recent Notable Change
1515

16-
Breaking change: the C# reduction boolean cluster is replaced by a single reduction level. The flags `--all`, `--skeleton`, `--public-api`, `--aggressive`, and the `--remove-csharp-*` switches are gone, replaced by one `--level` option (and a matching `level` MCP parameter) with the values `none`, `standard`, `aggressive`, `skeleton`, and `publicApi`. The CLI commands default to `none`; the scoped MCP tools (`fuse_focus`, `fuse_search`, `fuse_changes`, `fuse_dotnet`) default to `standard`, so an agent gets the standard removals (which preserve 99 to 100 percent of the public API surface on the benchmark corpus) without specifying a level. Migrate `--all` to `--level aggressive` (add `--collapse-generated` if you relied on `--all` collapsing generated code), `--aggressive` to `--level aggressive`, `--skeleton` to `--level skeleton`, `--public-api` to `--level publicApi`, and any `--remove-csharp-*` flag to `--level standard`, which performs all four removals together. The redaction, generated-code collapse, semantic-marker, pattern-summary, route-map, project-graph, and minification flags are unchanged and remain orthogonal to the level.
16+
Breaking change (2.2): `fuse serve` moved to `fuse mcp serve`. The MCP server is now a subcommand of a new `fuse mcp` group, alongside `fuse mcp install`, which registers Fuse with Claude Code, Cursor, or GitHub Copilot in one command instead of hand-editing JSON. Client configuration that launched `fuse serve` must change its arguments from `["serve"]` to `["mcp", "serve"]`; re-running `fuse mcp install` rewrites them. See [Connect to your AI](/docs/start/connect-your-ai) for the current setup flow.
17+
18+
Prior breaking change (2.1): the C# reduction boolean cluster is replaced by a single reduction level. The flags `--all`, `--skeleton`, `--public-api`, `--aggressive`, and the `--remove-csharp-*` switches are gone, replaced by one `--level` option (and a matching `level` MCP parameter) with the values `none`, `standard`, `aggressive`, `skeleton`, and `publicApi`. The CLI commands default to `none`; the scoped MCP tools (`fuse_focus`, `fuse_search`, `fuse_changes`, `fuse_dotnet`) default to `standard`, so an agent gets the standard removals (which preserve 99 to 100 percent of the public API surface on the benchmark corpus) without specifying a level. Migrate `--all` to `--level aggressive` (add `--collapse-generated` if you relied on `--all` collapsing generated code), `--aggressive` to `--level aggressive`, `--skeleton` to `--level skeleton`, `--public-api` to `--level publicApi`, and any `--remove-csharp-*` flag to `--level standard`, which performs all four removals together. The redaction, generated-code collapse, semantic-marker, pattern-summary, route-map, project-graph, and minification flags are unchanged and remain orthogonal to the level.
1719

1820
Fuse 2.0 is a structural rewrite. It replaces the monolithic layers with an axis-based layout split into Core pipeline libraries, a Host for the CLI and MCP server, and language plugins. Backward compatibility with 1.x output is not a goal; the changelog includes a migration table covering the MCP tool changes, the default tokenizer change to `o200k_base`, the manifest header, and secret redaction now defaulting on.
1921

site/content/docs/project/performance.mdx

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,7 @@ title: Performance and Benchmarking
33
description: How Fuse keeps fusion fast, what each performance feature does, and how to measure cold-start and pipeline timing.
44
---
55

6-
Fuse runs in two shapes with different performance profiles. One-shot commands such as `fuse dotnet` and `fuse init` pay a fixed cost on every invocation: process startup, dependency injection graph construction, and tokenizer initialization. On small repositories that fixed cost can dominate wall time. The long-running `fuse serve` (MCP) server stays resident, so startup is paid once per session and pipeline work dominates from then on. This page describes the features that govern fusion speed and the method for measuring it.
6+
Fuse runs in two shapes with different performance profiles. One-shot commands such as `fuse dotnet` and `fuse init` pay a fixed cost on every invocation: process startup, dependency injection graph construction, and tokenizer initialization. On small repositories that fixed cost can dominate wall time. The long-running `fuse mcp serve` (MCP) server stays resident, so startup is paid once per session and pipeline work dominates from then on. This page describes the features that govern fusion speed and the method for measuring it.
77

88
This page is for engineers tuning a fusion run and maintainers comparing builds. A reader who only needs the timing numbers can skip to How To Run The Benchmarks.
99

0 commit comments

Comments
 (0)