Capability and Plugin Model
How Fuse keeps language behavior in plugins and resolves it by file extension through capability registries.
Fuse has two extension-driven seams. Reduction and presentation use capability interfaces from the plugin abstractions. Persistent syntax indexing uses ILanguageSyntaxProvider to extract language-tagged symbols and chunks. Typed semantic analysis is separate and remains C#-only.
This page is for engineers who want to understand the plugin boundary and for contributors adding support for a new language or format.
Architectural Rationale
Extension registries keep reducer selection and syntax extraction out of per-file switch statements. A registered capability claims extensions, and later registrations win a conflict. This does not make every tier language-neutral: compiler-backed graph construction, verification, and refactoring use the C# Roslyn path.
Index Language Tiers
The persistent index selects a syntax provider by extension:
| Provider | Extensions | Output |
|---|---|---|
| C# | .cs | Roslyn-syntax symbols and chunks tagged csharp |
| Python | .py | Bounded lexical class/function symbols and chunks tagged python |
| JavaScript | .js, .jsx, .mjs, .cjs, .ts, .tsx, .mts, .cts | Bounded lexical class/function symbols and chunks tagged javascript |
These records support exact lookup, full-text search, and task localization through language-agnostic tables. Python and JavaScript do not produce typed edges, compiler signatures, route or dependency wiring, build-capture verification, or compiler-executed refactors.
The maintained Python and JavaScript providers are frozen at their current syntax scope. A first-party semantic provider for another language requires that language's real compiler service, not another parser or regex layer.
Registration through Dependency Injection
Language behavior is registered with the service container, not hard-coded. The default composition registers the C# language plugin and the built-in format reducers:
services.AddCSharpLanguage(); // C# reducer, skeleton, markers, dependencies, type locator, maps, detectors
services.AddFormatReducers(); // reducers for HTML, JSON, YAML, XML, and other formatsA host that wants a different set of languages calls the core registration directly and composes its own plugins on top.
The Capability Contracts
Every capability extends the base contract, which declares the file extensions it handles. Resolution is by extension, matched case-insensitively, each including its leading dot.
| Interface | Responsibility |
|---|---|
IContentReducer | Reduce a file's content for its extension |
ISkeletonExtractor | Produce a signatures-only structural skeleton |
ISemanticMarkerGenerator | Generate type-level annotation comments |
IDependencyExtractor | Extract referenced type names for the dependency graph |
ITypeNameLocator | Resolve a type name to the file or files that define it |
ISymbolOutlineExtractor | Produce a per-file symbol outline for the workspace map |
ISymbolSliceExtractor | Reduce a file to one member, keeping its body and signatures only for the rest |
IRouteMapGenerator | Produce an endpoint table for the workspace map |
IProjectGraphGenerator | Produce a solution and project reference graph |
IPatternDetector | Detect a cross-codebase convention across the indexed files |
ISymbolOutlineExtractor and ISymbolSliceExtractor live in Fuse.Plugins.Abstractions alongside the other contracts. The outline extractor backs the table-of-contents survey; the slice extractor backs Type.Member focus scoping.
Pattern detectors are the exception to per-extension resolution. They derive from a batch base class that runs a reset, one accumulate call per file, and a finalize call, so a detector folds signals across the whole fused set in a single pass rather than being resolved for one file. Detectors are stateful and run one batch at a time.
Capability Registries
A capability registry builds an extension-to-capability map at startup. It iterates every registered implementation, and for each extension that implementation declares, it records the implementation under that extension. The pipeline then resolves a capability by passing a file's extension; the registry returns the registered implementation or nothing when no capability handles that extension.
Last registration wins. When two implementations declare the same extension, the one registered later replaces the earlier one in the map. A specialized plugin can therefore override a default by registering after it. Resolution returning nothing is a normal outcome: a file whose extension has no registered reducer passes through reduction unchanged, and a file with no registered dependency extractor contributes an empty reference list to the graph.
C# reduction capabilities follow this rule in the default host. The C# language plugin registers the content reducer, project-graph generator, and pattern detectors. The Roslyn plugin supplies structural C# extractors. The separate persistent syntax index selects ILanguageSyntaxProvider implementations and stores a language tag per file.
The Five Registries
The core registration builds five registries, one per resolvable-by-extension capability that the pipeline consults during collection-to-reduction work:
IContentReducerISkeletonExtractorISemanticMarkerGeneratorIDependencyExtractorITypeNameLocator
The remaining reduction capabilities (route map and project graph generators) are resolved as single optional services, and pattern detectors run as a batch. These registries do not define the typed semantic tier.
What This Does Not Cover
This page describes the capability boundary and resolution. It does not document the internal algorithms of any specific capability, such as how the dependency extractor or the full-text index work; see Retrieval internals. It does not give a step-by-step plugin walkthrough.
Next
See Extending Fuse With A Language Plugin to implement and register a new language. See The Fusion Pipeline for where each capability is consulted, and Core Concepts for the conceptual overview.
Shared daemon
One Fuse daemon per repository holds the warm compilation as a shared asset, so multiple agent sessions and the ambient hooks read one resident workspace instead of each paying its own cold start and memory.
Retrieval Internals
The candidate generators, score normalization, and typed graph expansion that implement localize, resolve, context, and review.