零依赖的 MCP 服务器,用于本地文件操作。 13 个文件系统工具 + 3 个元工具用于渐进式发现 — 无需 SDK、无需框架、无需 npm install。
MCP 协议: 2024-11-05 · 传输: stdio + Streamable HTTP · 运行时: Node.js ≥ 22.0.0
local-mcp.mjs — 595 lines, 13 tools, entry point
lib/mcp-core.mjs — 229 lines, stdio + HTTP transport, 9 MCP methods
lib/config.mjs — 31 lines, MCP_WORKSPACE/DATA env config with validation
总计:~855 行,零运行时依赖。
| 工具 | 描述 | 注解 |
|---|---|---|
read | 读取文件并显示行号,可选 head/tail 截断 | readOnlyHint |
search | 按名称(glob)搜索文件,再按内容(grep)搜索 | readOnlyHint |
ls | 紧凑的目录列表,带惰性 stat | readOnlyHint |
exec | 流式命令执行,支持 stdin 和超时 | destructiveHint |
diff | 比较两个文件或文本字符串(Myers O(ND)) | readOnlyHint |
copy | 复制文件或目录 | destructiveHint |
move | 移动或重命名文件/目录 | destructiveHint |
batch | 顺序执行多个操作;原子回滚,$prev 引用 | destructiveHint |
file | 统一操作:读取、写入、编辑、追加、删除、信息、创建目录、移动 | — |
block | 按范围或函数名读取/替换/插入/删除代码块 | — |
bookmark | 持久化路径别名(添加/获取/列出/删除) | — |
grep | 紧凑的 file:line:content 格式,带自适应并发 | readOnlyHint |
watch | 监视文件/目录变化;最多 20 个并发监视器 | — |
| 工具 | 描述 |
|---|---|
search_tools | 按关键字搜索可用工具 — 相比列出所有工具节省约 90% 的 token |
describe_tool | 获取特定工具的完整输入模式(按需加载) |
call_tool | 按名称和参数执行任意工具 |
与其在每个请求中发送全部 13 个工具模式(约 3,000 token),这 3 个元工具实现的渐进式发现将其减少到约 50 token — 节省约 90% 的 token。
| # | 优化项 | 影响 |
|---|---|---|
| A | 流式头部/尾部读取 | streamHead() 避免读取整个文件。500MB 日志:3s → 5ms,内存:500MB → 几 KB |
| B | ls 中的惰性 stat | 仅在 sort=size 时调用 statSync。1000 个文件的目录:50ms → 2ms |
| C | 自适应 grep 并发 | 使用 os.availableParallelism()(最大 16,最小 4)替代硬编码的 16 个工作线程 |
| D | LRU 缓存逐出 | 基于 Map 插入顺序的 LRU — 热的小文件不再被冷的大文件逐出 |
| E | Grep 字节保护 | MAX_GREP_TOTAL_MB=100 + MAX_GREP_FILES=1000 防护防止 OOM |
| F | 进度通知 | 为 MCP 2025 规范传递 _meta.progressToken(TODO:长时间执行的 events) |
| 区域 | 详情 |
|---|---|
| 读取缓存 | 大小感知的逐出(最多 50 项,10 MB)+ 5 秒 TTL |
| Myers 差异 | O(ND) 算法,由 edit、block 和 diff 使用 |
| 搜索评分 | 优先名称匹配(无 I/O),然后仅对前 50 个候选进行 stat |
| 输出格式 | grep:file:line:content,ls:紧凑列,read:行号 + 截断提示 |
| 协议 | O(1) Map 分发,同步处理短路 |
# Zero install — no dependencies
node local-mcp.mjs
# With configuration
MCP_WORKSPACE=D:/projects node local-mcp.mjs
{
"mcpServers": {
"local-mcp": {
"command": "node",
"args": ["D:/path/to/local-mcp.mjs"],
"env": {
"MCP_WORKSPACE": "D:/projects"
}
}
}
}
node local-mcp.mjs --http
node local-mcp.mjs --http --port 3456
支持 JSON-RPC 2.0 POST、SSE 流式传输(Accept: text/event-stream)、CORS 和 GET /tools。
node local-mcp.mjs --help # Show usage + env vars
node local-mcp.mjs --list-tools # Print available tools and exit
node local-mcp.mjs --http # Start HTTP mode
node local-mcp.mjs --http --port 3456
| 变量 | 默认值 | 描述 |
|---|---|---|
MCP_WORKSPACE | process.cwd() | 工作目录根路径(安全边界) |
MCP_DATA | {WORKSPACE}/.mcp-data | 数据目录(书签、临时文件) |
MCP_DIR | {WORKSPACE} | tree/ls 命令的默认目录 |
MCP_PORT | 3100 | HTTP 服务器端口(使用 --http 时) |
MCP_READONLY | false | 设置为 true 以阻止所有写操作 |
MCP_EXCLUDE | — | 逗号分隔的额外目录,从搜索中排除 |
MCP_WORKSPACE 及其子目录内__proto__/constructor/prototype 注入).gitignore 和常见的排除目录(node_modules、.git 等)零运行时依赖。 仅使用 Node.js 内置模块:
| 模块 | 用途 |
|---|---|
fs | 文件系统 + glob(Node 22) |
child_process | 流式 shell 执行 |
http | HTTP 传输(无需 Express) |
path | 路径解析 |
os | availableParallelism() 用于自适应并发 |
readline | 流式逐行处理 |
ls 中的惰性 stat:1000 个文件的目录 50ms → 2msavailableParallelism() 的自适应 grep 并发streamHead 作用域错误 — done 在 Promise 回调外定义# Run tests
node --test test/*.test.mjs
# Adding a tool
# 1. Define schema + handler in local-mcp.mjs
# 2. Register with server.tool()
# 3. Add tests
MIT