关于 SilverBullet
silverbullet-mcp 是连接 SilverBullet 空间的轻量 MCP 服务,适用于需要通过 Agent 管理 Markdown 页面的人。它转发请求至 SilverBullet 内置的 `/.fs` API,无需修改或安装到 SilverBullet 中。
主要功能
- 01列出、读取 Markdown 页面
- 02创建、覆盖和追加页面
- 03删除页面并搜索内容
- 04支持 stdio 与流式 HTTP
- 05HTTP 模式使用 Bearer Token
适用场景
- 01让 Agent 查询 SilverBullet 笔记
- 02通过 Agent 新建或追加项目文档
- 03在多个客户端间共享远程页面访问
MCP 相关
服务向 MCP 客户端提供六种页面列表、读写、追加、删除和搜索工具。支持 stdio 与流式 HTTP 两种传输方式。
配置
本地服务的配置在各客户端中通用,复制后粘贴到客户端的 MCP 配置文件即可。
工具
本地服务需要在你的电脑上运行后才能读取工具,维护者暂未提供工具列表。
详细介绍
silverbullet-mcp
一个小巧的 MCP 服务,让任何支持 MCP 的 Agent 都能读写 SilverBullet 空间。
无依赖——仅使用 Python 3 标准库。它是一个转换器:将 MCP 工具调用转发到 SilverBullet 内置的 /.fs HTTP API,该 API 已支持读取、写入和删除。无需在 SilverBullet 内部安装或修补任何内容。
它足够小巧,一次就能读完;并且支持客户端实际使用的两种 MCP 传输方式:stdio(由 Claude Desktop、Cursor 等启动) 和 streamable HTTP(通过反向代理实现共享或远程访问)。
快速开始
将其作为服务运行:
git clone https://github.com/wicahma/silverbullet-mcp.git
cd silverbullet-mcp
cp .env.example .env # set MCP_TOKEN, and SB_URL if SilverBullet is elsewhere
set -a; . ./.env; set +a
python3 sb_mcp.py # streamable HTTP on http://127.0.0.1:9339/mcp
也可以让客户端启动它——它已发布到 npm,无需克隆:
SB_URL=http://127.0.0.1:8123 npx -y silverbullet-mcp --stdio
工具
| 工具 | 参数 | 功能 |
|---|---|---|
list_pages | — | 列出所有 Markdown 页面 |
read_note | path | 读取页面 |
write_note | path、content | 创建或覆盖页面 |
append_note | path、content | 追加内容;页面不存在时创建 |
delete_note | path | 删除页面 |
search_notes | query | 不区分大小写的子字符串搜索,返回 path:line: text |
路径相对于空间(Projects/Foo.md),仅限 .md 文件,并且会拒绝包含 .. 的路径段。
传输方式
| stdio | streamable HTTP | |
|---|---|---|
| 启动 | --stdio,或 MCP_STDIO=1 | 默认 |
| 帧格式 | 通过 stdin/stdout 传输以换行符分隔的 JSON-RPC | POST /mcp |
| 身份验证 | 无——客户端已拥有该进程 | Authorization: Bearer $MCP_TOKEN |
| 适用场景 | Claude Desktop、Cursor,以及任何会启动该服务的客户端 | 远程或共享访问、反向代理、多个客户端 |
两种传输方式使用相同的代码,并提供相同的六种工具。MCP_TOKEN 仅在 HTTP 模式下生效;SB_* 变量在两种模式下都用于指定上游空间。
客户端配置
Claude Desktop
编辑 ~/Library/Application Support/Claude/claude_desktop_config.json(macOS)或
%APPDATA%\Claude\claude_desktop_config.json(Windows):
{
"mcpServers": {
"silverbullet": {
"command": "npx",
"args": ["-y", "silverbullet-mcp", "--stdio"],
"env": { "SB_URL": "http://127.0.0.1:8123" }
}
}
}
Cursor
内容相同;单个项目使用 .cursor/mcp.json,全局配置使用 ~/.cursor/mcp.json。
任何支持远程 MCP 的客户端
{
"mcpServers": {
"silverbullet": {
"type": "http",
"url": "https://your-host.example/mcp",
"headers": { "Authorization": "Bearer <MCP_TOKEN>" }
}
}
}
本地使用,前面不经过反向代理:
{
"mcpServers": {
"silverbullet": {
"type": "http",
"url": "http://127.0.0.1:9339/mcp",
"headers": { "Authorization": "Bearer <MCP_TOKEN>" }
}
}
}
远程客户端须知:url 必须指向此桥接服务,或代理到此桥接服务——不能指向 SilverBullet 本身。SilverBullet 没有自己的 MCP 端点;本项目正是为此添加该端点。
配置
所有配置都通过环境变量设置,因此任何人都可以运行相同的代码。
| 变量 | 默认值 | 含义 |
|---|---|---|
MCP_TOKEN | (空) | HTTP 模式下必需。 客户端必须发送的 Bearer 令牌。使用 python3 -c "import secrets; print(secrets.token_urlsafe(32))" 生成 |
SB_URL | http://127.0.0.1:8123 | SilverBullet 基础 URL。必须提供 /.fs |
SB_AUTH_TOKEN | (空) | 可选。以 Authorization: Bearer ... 的形式发送给 SilverBullet |
SB_USER_AGENT | silverbullet-mcp/1.0 | 在上游调用中发送。某些 CDN 会对 Python 默认的 urllib 标识返回 403 / 错误 1010 |
MCP_HOST | 127.0.0.1 | 绑定地址 |
MCP_PORT | 9339 | 绑定端口 |
MCP_STDIO | (未设置) | 设置任意值即可切换到 stdio,与 --stdio 效果相同 |
HTTP 端点
POST /mcp— JSON-RPC 2.0。需要 Bearer 令牌。通知请求返回202。GET /health(也可使用GET /mcp/health)—{"status":"ok"},无需身份验证,不返回内部详情。
协商的协议版本:2024-11-05、2025-03-26、2025-06-18。
请求正文最大为 4 MB。接受批量请求数组。
身份验证
Bearer 令牌是访问关卡。默认拒绝:如果设置了 MCP_TOKEN,所有未提供匹配令牌的请求都会被拒绝。如果未设置,服务仍会启动(用于本地调试),但会记录醒目的警告。
未设置令牌时,请勿将此服务暴露到互联网。 任何能访问 /mcp 的人都可以读取、覆盖和删除空间中的所有页面。
SilverBullet 自身的身份验证
在较新的 SilverBullet 构建版本中(已在 Rust 构建版本 2.10.0 上验证),仅设置 SB_AUTH_TOKEN 不会启用身份验证——匿名请求仍会成功。根据上游文档,该令牌只是另一种 bearer 验证方式;只有配置了 SB_USER,服务器才会实际强制执行身份验证。如有疑问,请使用故意错误的 bearer 令牌测试自己的实例:如果仍然返回 200,则身份验证未启用。
实际做法:在此桥接服务(或反向代理)上设置令牌验证,而不是在 SilverBullet 上设置。
部署
systemd 用户单元
[Unit]
Description=SilverBullet MCP bridge
After=network-online.target
[Service]
EnvironmentFile=%h/silverbullet-mcp.env
WorkingDirectory=%h/silverbullet-mcp
ExecStart=/usr/bin/python3 sb_mcp.py
Restart=on-failure
[Install]
WantedBy=default.target
将环境文件的权限模式设为 600。
位于反向代理之后
可与 Cloudflare Tunnel、nginx、Caddy 等配合使用。以下是实际部署中总结出的两点经验:
- 如果使用免费 TLS 方案,请通过现有主机名上的路径进行路由:某些服务商只会为顶级域名和单层子域名颁发证书,因此两层子域名可能无法完成 TLS 握手。通过已有证书覆盖的主机进行路径路由即可完全避免此问题。
- 机器客户端无法完成 SSO。如果你的主机位于身份感知代理(如 Cloudflare Access)之后,请绕过 MCP 路径,并使用 bearer 令牌进行验证。这是常见的划分方式:SilverBullet UI 和其
/.fsAPI 仍由 SSO 保护,而/mcp对外开放,但需通过令牌验证。
故障排除
| 症状 | 原因 |
|---|---|
401 unauthorized | 客户端请求头中的 MCP_TOKEN 缺失或错误 |
403,并显示 error code: 1010 | CDN/WAF 拒绝了上游请求签名。请将 SB_USER_AGENT 设置为可识别的值,并允许 API 路径上的机器客户端访问 |
上游返回 HTML 登录页面,或桥接服务报告 JSONDecodeError | SB_URL 指向了 SSO 保护下的 UI。请将其指向 /.fs 确实可访问的地址(localhost 或内部主机名) |
HttpError 500 / 502,并提及上游 | 桥接服务正常;SilverBullet 已停止运行,或 SB_AUTH_TOKEN 错误 |
| 编辑配置后客户端中缺少工具 | 重启客户端——MCP 服务会在启动时连接 |
npx 立即退出 | python3 不在 PATH 中;npm 包装器只是用于启动 sb_mcp.py |
安全说明
- 路径仅限
.md,并会拒绝包含..的路径遍历片段。 write_note会覆盖内容,且不保留修订历史。- 默认绑定到 loopback;反向代理是唯一入口。
search_notes每次调用都会读取所有页面。没有索引。- 桥接服务不存储任何内容。除启动时读取的环境外,它不保留任何状态,因此重启始终安全。
分发
通过 npm 包以及来自同一仓库的 Agent 插件发布。
npm publish --access public # package "silverbullet-mcp"
server.json 是官方 MCP Registry 条目(架构 2025-12-11):npm 包通过 stdio 运行。它有意不声明远程端点——每个部署都有自己的 URL,因此如果想列出自己的服务,请添加 remotes 条目。
brew install mcp-publisher
mcp-publisher login github
mcp-publisher validate # validates server.json
mcp-publisher publish
Registry 名称采用反向 DNS 格式,且必须与发布所用的 GitHub 账户匹配:发布前,请将 server.json("name")和 package.json("mcpName")中的 OWNER 替换为你的 GitHub 登录名——两者必须完全一致。
Agent 插件清单位于 .zcode-plugin/plugin.json(ZCode)以及 .claude-plugin/plugin.json + .claude-plugin/marketplace.json(Claude Code 和 skills.sh 布局)中。插件包含 MCP 服务和 skills/silverbullet-mcp/,并从客户端的用户配置中读取 bearer 令牌,键名为 mcp_token,因此仓库中不会存储机密。
许可证
MIT
评论
一个开放协议,规定了 AI 应用如何以统一方式连接外部工具与数据源。客户端负责与模型对话,MCP 服务负责提供工具、资源和提示模板,两者通过标准消息通信,同一个服务可以被不同客户端复用。