使用说明
Raindrop.io MCP服务器
Raindrop.io的模型上下文协议(MCP)服务器。它通过OAuth或直接令牌认证的Streamable HTTP向MCP客户端公开书签、集合、标签和突出显示。
特性
- 收藏:列表、管理、合并、清理、重新排序、封面上传
- 书签:搜索、创建/更新/删除、批量创建/删除、文件/封面上传
- 标签:列表、重命名、合并、删除
- 亮点:列表、创建、更新、删除
- OAuth 2.0+PKCE或直接令牌认证
- Cloudflare Workers部署,配备Workers KV支持的OAuth存储
需求
- Bun 1.0+
- 启用Workers的Cloudflare帐户
- Raindrop.io帐户
- 一种身份验证方法:
- Raindrop OAuth应用程序+Workers KV,或
- 雨滴API代币
设置
安装依赖项:
bun install
环境变量
OAuth(建议用于生产环境):
OAUTH_CLIENT_IDOAUTH_CLIENT_SECRETOAUTH_REDIRECT_URI(例如。https://raindrop-mcp.anuragd.me/auth/callback)OAUTH_ALLOWED_REDIRECT_URIS(逗号分隔)TOKEN_ENCRYPTION_KEY(64个十六进制字符)JWT_SIGNING_KEYRAINDROP_AUTH_KV配置了工人KV绑定wrangler.jsonc
直接令牌回退(单用户):
RAINDROP_ACCESS_TOKENALLOW_ENV_TOKEN_AUTH=true
部署范围广 RAINDROP_ACCESS_TOKEN 不建议将回退用于生产。它仅在以下情况下处于活动状态 ALLOW_ENV_TOKEN_AUTH 明确设置为 true;更喜欢OAuth或按请求 X-Raindrop-Token 用于生产用途的身份验证。
部署(Cloudflare Workers)
bunx wrangler login
bun run cf:kv:create
# copy the printed KV ids into wrangler.jsonc, then set secrets with wrangler
bun run deploy:cloudflare
看 文档/部署.md 用于完整的Cloudflare设置和烟雾测试。
托管服务器
使用生产MCP端点:
https://raindrop-mcp.anuragd.me/mcp
支持OAuth的MCP客户端将:
- 发现
/.well-known/oauth-protected-resource. - 发现
/.well-known/oauth-authorization-server. - 注册
/register. - 打开
/authorize使用PKC。 - 当不存在Raindrop会话时,通过Raindrop OAuth发送给您。
- 在以下位置交换授权码
/token. - 呼叫
/mcp持有已发行的不记名代币。
MCP客户端配置
{
"mcpServers": {
"raindrop": {
"url": "https://raindrop-mcp.anuragd.me/mcp",
"transport": "streamable-http"
}
}
}
如果使用直接令牌身份验证:
{
"mcpServers": {
"raindrop": {
"url": "https://raindrop-mcp.anuragd.me/mcp",
"transport": "streamable-http",
"headers": {
"X-Raindrop-Token": "your_token"
}
}
}
}
端点
| 终点 | 目的 |
|---|---|
GET / |
公共登录页面 |
GET /docs/ |
静态设置/参考文档 |
GET /info |
公共JSON功能摘要 |
POST /mcp |
MCP可流式HTTP端点 |
GET /.well-known/oauth-protected-resource |
受保护的资源元数据 |
GET /.well-known/oauth-authorization-server |
授权服务器元数据 |
POST /register |
动态客户端注册 |
GET /authorize |
MCP OAuth授权条目 |
POST /authorize |
同意批准/拒绝 |
POST /token |
授权码和刷新令牌交换 |
GET /auth/init |
内部Raindrop OAuth启动 |
GET /auth/callback |
内部Raindrop OAuth回调 |
工具
收藏:
collection_listcollection_children_listcollection_managecollection_bulk_deletecollection_reordercollection_expandcollection_mergecollection_cleancollection_empty_trashcollection_cover_uploaduser_stats
书签:
bookmark_searchbookmark_managebookmark_cachebookmark_suggest_existingbookmark_bulk_createbookmark_bulk_deletebookmark_file_uploadbookmark_cover_uploadbulk_edit_bookmarksbookmark_statistics
标签:
tag_listtag_manage
亮点:
highlight_manage
建筑
graph TB
subgraph "Client Layer"
Browser[Web Browser]
MCPClient[MCP Client SDK]
end
subgraph "Transport Layer"
Worker["Cloudflare Worker\nsrc/worker.ts"]
end
subgraph "Authentication Layer"
OAuth["OAuth Service\nPKCE Flow"]
TokenStorage["Token Storage\nAES-256 Encrypted"]
WorkersKV["Workers KV\nRAINDROP_AUTH_KV"]
OAuth --> TokenStorage
TokenStorage --> WorkersKV
end
subgraph "MCP Protocol Layer"
MCPService["MCP Server\nMCP SDK web transport"]
end
subgraph "Service Layer"
RaindropService["RaindropService\nAPI Client\nopenapi-fetch"]
end
subgraph "External Services"
RaindropAPI[Raindrop.io API]
end
MCPClient -->|HTTP| Worker
Browser -->|HTTPS| Worker
Worker -->|MCP auth wrapper| OAuth
OAuth -->|Validated Token| MCPService
MCPService -->|Per-User Token| RaindropService
RaindropService -->|HTTP Requests| RaindropAPI
OAuth流
sequenceDiagram
participant User
participant Client as Client App
participant Worker as Cloudflare Worker
participant OAuth as OAuth Service
participant KV as Workers KV
participant Raindrop as Raindrop.io
User->>Client: Add MCP endpoint
Client->>Worker: GET /.well-known/oauth-protected-resource
Worker->>Client: Protected resource metadata
Client->>Worker: GET /.well-known/oauth-authorization-server
Worker->>Client: Authorization metadata
Client->>Worker: POST /register
Worker->>KV: Store OAuth client
Client->>Worker: GET /authorize with PKCE + resource
Worker->>Client: Redirect to /auth/init when no Raindrop session exists
Client->>Worker: GET /auth/init
Worker->>Raindrop: Authorization request
Raindrop->>User: Consent
User->>Raindrop: Approve access
Raindrop->>Worker: GET /auth/callback?code=XXX&state=YYY
Worker->>KV: Store encrypted Raindrop token
Worker->>Client: Continue /authorize consent
User->>Worker: Approve MCP client
Worker->>KV: Store authorization code
Worker->>Client: Redirect with code
Client->>Worker: POST /token
Worker->>Client: JWT access token
Client->>Worker: POST /mcp (Bearer JWT)
Worker->>KV: Fetch encrypted Raindrop token
Worker->>Raindrop: MCP operation with Raindrop token
Raindrop->>Worker: Response
Worker->>Client: MCP result
多租户模型
graph LR
subgraph "Shared Server Instance"
Endpoint["MCP Endpoint\n/mcp"]
Auth[Auth Layer]
subgraph "Request-Scoped Services"
Service1["RaindropService\nUser 1 Token"]
Service2["RaindropService\nUser 2 Token"]
Service3["RaindropService\nUser 3 Token"]
end
end
subgraph "Users"
User1[User 1]
User2[User 2]
User3[User 3]
end
subgraph "Storage"
KV["Workers KV"]
end
User1 -->|Bearer JWT| Endpoint
User2 -->|X-Raindrop-Token| Endpoint
User3 -->|Bearer JWT| Endpoint
Endpoint --> Auth
Auth --> KV
Auth -->|Token A| Service1
Auth -->|Token B| Service2
Auth -->|Token C| Service3
Service1 --> API[Raindrop.io API]
Service2 --> API
Service3 --> API
发展
bun run dev
bun run type-check
bun test
故障排除
- 401:缺少身份验证(OAuth流未完成或没有X-Raindrop-Token)
- 406:客户端必须发送
Accept: application/json, text/event-stream - 500:检查日志和令牌有效性
许可证
麻省理工学院
