关于 codereach-mcp
CodeReach 是面向 ASP.NET Core 和 C# 解决方案的 MCP 服务,利用 Roslyn 构建调用图,追踪代码关联的端点与作业。开发者可通过 Agent 或命令行检查路由、依赖、符号引用和变更影响。
主要功能
- 01基于 Roslyn 语义模型构建调用图
- 02追踪符号关联的端点与作业
- 03将 Git 差异映射到受影响入口
- 04检查路由与授权信息
- 05分析依赖注入注册
- 06在磁盘索引并增量更新
适用场景
- 01查找调用某方法的 API 路由
- 02识别差异影响的端点与作业
- 03审计缺少授权的路由
- 04追踪服务与存储库调用
MCP 相关
向 MCP 客户端提供分析工具和预设提示词,包括调用追踪、路由列表、引用搜索和变更影响报告。
配置
本地服务的配置在各客户端中通用,复制后粘贴到客户端的 MCP 配置文件即可。
我们还没有获取到这个服务的安装包或远程地址,请按项目 README 中的说明安装。
工具
本地服务需要在你的电脑上运行后才能读取工具,维护者暂未提供工具列表。
详细介绍
CodeReach
哪些端点和作业会触达这段代码,你的差异会影响什么。
CodeReach 是面向 ASP.NET Core 和 C# 解决方案的 MCP 服务。它使用 Roslyn 加载你的解决方案,根据编译器自己的语义模型构建调用图并将其保存在磁盘上,然后回答 Agent(或你在 shell 中)原本需要通过 grep 和猜测才能回答的问题:
- 哪些代码会调用此方法,通过它的接口一路追溯到控制器操作、minimal API 处理程序或后台服务?
- 存在哪些端点,其完整路由和授权是什么,包括你自己的权限特性?
- 我修改了这些行。会影响哪些端点和作业?
状态:0.1.0,尚未发布到 NuGet。以下使用 dnx 的命令将在发布后生效。
为什么不用 grep 或 tree-sitter 索引
文本和语法工具看不到编译器所看到的内容。在分层应用程序(控制器、服务接口、服务、存储库接口、存储库)中,它们会止步于第一个接口,统计注释和字符串,将调用关联到错误的重载,并把共享的泛型基类方法报告为每个存储库的热点。CodeReach 使用 Roslyn 绑定每个名称,因此:
- 通过
IOrderService发起的调用会追溯到OrderService,并明确指出这一点; PermissionKeys.Orders.Delete和PermissionKeys.Products.Delete是不同的符号;OrderRepository.GetByIdAsync只统计OrderRepository可能接收到的调用,即使该方法实际定义在Repository<T>中;- 测试会被排除,因为它们的项目引用了测试框架,而不是因为名称;
- 每个工具都读取同一张图,因此调用方数量、使用次数和追踪结果始终一致。
运行
需要 .NET 10 SDK,以及一个能够成功构建的解决方案。
{
"mcpServers": {
"codereach": {
"command": "dnx",
"args": ["CodeReach.Mcp", "--yes"]
}
}
}
服务器会索引其工作目录中的单个 .slnx、.sln 或 .csproj。若要指定其他位置,请在 args 中追加 "--", "--solution", "path/to/App.slnx"。
从本仓库克隆开始:
dotnet run --project src/CodeReach.Mcp -- call trace_to_entrypoints '{"symbol":"OrderRepository.HardDeleteAsync"}' --solution samples/SampleShop
entry points that reach OrderRepository.HardDeleteAsync(Guid)
4 entry points (3 endpoint, 1 hosted-service), 1 unrooted tops; 10 symbols visited. Hidden: 2 call sites in test projects (include_tests=true shows them).
[endpoint] DELETE /api/Orders/{id:guid} auth: HasPermission(PermissionKeys.Orders.Delete = "orders.delete") [action]; Authorize [base ShopControllerBase]
OrdersController.Delete(Guid) src/Shop.Api/Controllers/OrdersController.cs:17
-> OrderPurger.PurgeAsync(Guid) called at src/Shop.Api/Controllers/OrdersController.cs:19 (bound to IOrderPurger.PurgeAsync(Guid))
-> OrderRepository.HardDeleteAsync(Guid) called at src/Shop.Application/Orders/OrderService.cs:47 (bound to IOrderRepository.HardDeleteAsync(Guid))
[hosted-service] OrderPurgeService
OrderPurgeService.ExecuteAsync(CancellationToken) src/Shop.Infrastructure/Jobs/OrderPurgeService.cs:9
-> OrderPurgeService.PurgeExpiredAsync() called at src/Shop.Infrastructure/Jobs/OrderPurgeService.cs:13
...
本地页面,方便查看而非提问
codereach ui --solution path/to/App.slnx
这会在浏览器中打开一个页面,提供命令栏(可输入方法、路由、impact 或 di)和健康报告:未配置授权的端点、被捕获的依赖项、未注册的服务,以及未提交的更改会触达哪些内容。该页面由工具自身通过 127.0.0.1 提供服务,使用一次性令牌,从与上述相同的工具获取回答,并在按下 Ctrl+C 时停止。不会在任何地方托管。
CodeReach 是一个纯粹的 MCP 服务,完全在你的计算机上运行:无需账户或托管服务,也不会向任何地方发送数据。它不会安装钩子、技能或 Agent 配置文件,不会修改你的客户端配置,也不会向它分析的解决方案写入任何内容。它的索引存放在你的用户缓存目录中。
工具
| 工具 | 解答内容 |
|---|---|
trace_to_entrypoints | 每个能到达某个符号的端点、托管服务和其他根节点,并为每个根节点提供一条调用路径 |
impact | 将 git diff(未提交的更改、基础引用或 diff 文本)映射到受影响的端点和作业 |
routes | 端点的 HTTP 方法、完整路由模板、处理程序和授权信息;auth=none 会列出未受保护的端点 |
callers / callees | 调用关系,解析接口调用和虚方法分派,直至指定深度 |
find_usages | 按类型列出绑定到某个符号的所有引用(调用、读取、写入、nameof、特性);适用于框架成员 |
find_symbol | 按名称查找声明 |
entrypoints | 跟踪可能停止的所有根节点 |
architecture | 项目、各项目实际依赖其他项目的程度、最常被调用的方法、实现最多的接口 |
type_hierarchy | 某类型继承和实现的内容、所有直接或间接派生自该类型的类型、其成员,以及每个成员实现或重写的内容 |
di_registrations | 所有 AddScoped/AddSingleton/AddTransient/TryAdd/键控/托管/AddHttpClient/AddDbContext 注册,以及每个构造函数请求的服务;报告 被俘获的依赖项、已注入但未注册的服务和重复注册 |
status / reindex | 索引状态和新鲜度;强制刷新 |
提示词
预先编写好的请求,用于告知 Agent 按顺序调用哪些工具。每个 MCP 客户端都会显示这些提示词;在
Claude Code 中,它们会显示为 /mcp__codereach__<name>。
| 提示词 | 功能 |
|---|---|
review-diff | 查看更改的影响:带授权信息的端点、作业、也必须修改的实现,以及 DI 问题 |
before-change | 查看更改某个符号的影响范围,以及覆盖该符号的测试 |
add-feature | 查找此处类似功能的构建方式,并按相同层次规划要添加的文件 |
audit-auth | 按风险排序,列出没有授权或允许匿名访问的端点 |
explain-endpoint | 追踪单个端点从路由到数据访问的完整过程,涵盖所有层 |
符号可写为 Type.Member、path/File.cs:line,或使用之前回答中的 ID。若名称有歧义,系统会拒绝并列出候选项。每个工具也可作为 shell 命令使用:
codereach call <tool> '{json}',成功回答时退出码为 0,发现问题时为 1,无法运行时为 2。
每个回答都会告知你
- 默认筛选器隐藏了多少内容。 “已隐藏:测试项目中有 7 个调用点。”
- 分析是否完整。 最后一行是
analysis: complete,或者在加载或绑定失败的项目或文档旁标注PARTIAL。只有分析完整时才会显示 0。 - 索引是否为最新。 若首行以
STALE开头,表示文件已更改且刷新仍在进行。 - 哪些内容无法检测。 若某条调用链到达没有调用方的位置,系统会将其报告为 无根节点(依赖注入、反射或死代码),而不是静默丢弃。
保持索引最新
大型解决方案的首次索引耗时与构建大致相同。之后,索引会作为文件保存:源文件未更改时启动的服务可在毫秒内响应,且不会加载 Roslyn。文件更改时,仅修改方法体的编辑会重新提取对应文档;声明更改则会重新提取对应项目及依赖该项目的项目。每次调用时都会检查新鲜度,不依赖文件监视。
配置
可选的 codereach.json,放在解决方案旁边:
{
// Attributes that mean authorization but implement no framework contract.
"authAttributes": ["HasPermission"],
// Fluent endpoint methods that mean authorization, besides RequireAuthorization.
"authEndpointMethods": ["RequirePermission"],
// Source that should not be indexed.
"exclude": ["**/Migrations/**"],
// Extra entry points: a method that implements an interface member, derives from a base type, or carries an attribute.
"entryPoints": [
{ "kind": "command-handler", "implements": "MyApp.ICommandHandler`1", "method": "HandleAsync" }
]
}
实现框架自身授权约定的特性无需配置即可识别;MediatR 处理程序、MassTransit 消费者、Quartz 作业、中间件、SignalR 集线器和 Azure Functions 也无需配置即可识别。
不建模的内容
- 隐式用户定义转换,以及
foreach、using、await、解构和集合初始值设定项背后的调用。 - 反射,以及依赖注入容器调用的构造函数(
di_registrations会读取注册本身,但通过程序集扫描或在库内部完成的注册除外)。 - 通过包含多个实现的接口进行的调用会报告给接收方静态类型允许的每个实现,并且每一跳都会说明候选项的数量。
- 全局授权(回退策略、全局授权筛选器)会被检测到,并列在路由列表旁边,而不会应用于单个端点。
- 传统(非特性)MVC 路由会标记为
(conventional)。 - 仅支持 C#。Razor Pages、gRPC 和 SignalR 可通过入口点规则访问,但不会列为路由。
开发
dotnet build
dotnet test --project tests/CodeReach.Tests
测试会索引 samples/SampleShop,这是一个虚构的小型分层应用,包含上面列出的所有陷阱;然后将结果与 Roslyn 自带的引用查找器、经过完整人工审查的路由表,以及每种增量编辑后从头创建的索引进行比较。设计和计划见 docs/ARCHITECTURE.md 和 docs/PLAN.md。
许可证
MIT
评论
一个开放协议,规定了 AI 应用如何以统一方式连接外部工具与数据源。客户端负责与模型对话,MCP 服务负责提供工具、资源和提示模板,两者通过标准消息通信,同一个服务可以被不同客户端复用。