zotero-claude-bridge
by HCLEMINI
README.md
# zotero-claude-bridge
让 [Claude Code](https://claude.com/claude-code) 通过 MCP 控制 Zotero 浏览器连接器,把网页里的论文自动抓取到本地 Zotero 库。
```
Claude Code CLI
│ MCP 工具调用(stdio)
▼
zotero-claude-bridge(本仓库,Python MCP server,内嵌 WebSocket server)
│ WebSocket ws://127.0.0.1:24731/bridge
▼
改造后的 Zotero Connector(claude-bridge.js,service worker 长连接)
│ 复用原有 translator + itemSaver
▼
本地 Zotero 桌面客户端(POST http://127.0.0.1:23119/connector/saveItems)
```
本仓库**只是桥**。它必须和改造后的 Zotero Connector 扩展(fork 仓库 `zotero-connectors-claude-code`)配合使用。
## 它解决什么
- 原生 Zotero Connector 只能"手动逐篇点图标保存",无法被程序驱动。
- `zotero-mcp` 只能操作 Zotero 库内的增删改查,**不能从网页提取元数据**。
- 本桥让 Claude Code 编程驱动 Connector 的几百个 translator:抓当前页 / 给 URL 列表批量入库,全部走原生存储路径进本地 Zotero。
## 前置条件
1. **改造后的 Connector 扩展**已构建并以"加载已解压扩展程序"方式装进 Chrome —— 见 connector 仓库的 `src/browserExt/claude-bridge.js` 与构建说明(`build/manifestv3/`)。
2. **Zotero 桌面客户端**正在运行(`http://127.0.0.1:23119/connector/ping` 可达)。本机未开云同步也能用,因为全程走本地客户端。
## 安装
```bash
cd zotero-claude-bridge
pip install -e . # 或 pip install -r requirements.txt
```
`pip install -e .` 后 `python -m zotero_claude_bridge` 与 `zotero-claude-bridge` 命令都可用。
## 注册到 Claude Code
任选其一:
**A. 命令行(推荐)**
```bash
claude mcp add zotero-claude-bridge \
--env ZCB_HOST=127.0.0.1 --env ZCB_PORT=24731 \
-- python -m zotero_claude_bridge
```
**B. 配置文件**(项目级 `.mcp.json` 或用户级 `~/.claude.json`):复制 `.mcp.json.example`。
注册后在 Claude Code 里即可用这些工具:
| 工具 | 作用 |
|---|---|
| `zotero_status` | 检查扩展连接 + Zotero 在线(先调它确认健康) |
| `zotero_capture_active_tab` | 抓浏览器当前活动 tab |
| `zotero_capture_url` | 后台开 tab 抓单个 URL,完成后关闭 |
| `zotero_capture_urls` | 批量抓(并发上限 5,单次上限 50) |
| `zotero_ping` | 调试往返 |
## 用法
在 Claude Code 里直接说:
- "把当前打开的这篇论文抓到 Zotero" → 调 `zotero_capture_active_tab`
- "把这 10 个 URL 的论文都抓到 Zotero:<url 列表>" → 调 `zotero_capture_urls`
返回结构化结果:
```json
{"success": true, "items": [{"title": "...", "itemType": "journalArticle",
"creators": [...], "DOI": "...", "url": "...", "key": "ABCD1234"}],
"durationMs": 3210}
```
## 先测桥(不装扩展)
```bash
# 终端1:起 MCP server(前台 stdio,等 Claude Code 调用)
python -m zotero_claude_bridge
# 终端2:起假扩展(模拟 Connector)
python scripts/fake_extension.py
```
在 Claude Code 调 `zotero_status` 应返回 `extension_connected: true`;调 `zotero_capture_active_tab` 返回一个 `FAKE PAPER` 条目。
## WebSocket 协议
仅 127.0.0.1,JSON 文本帧:
```
{v:1, id?, type, action?, data?, ts}
```
- `type`:`auth | auth_ok | request | response | notification | error | heartbeat`
- `action`:`ping | get_status | capture_active_tab | capture_url | capture_urls`
- 鉴权(MVP):loopback 信任 + 扩展首帧 `auth` → server 回 `auth_ok`。
- 心跳:双向 30s,60s 无帧则断;扩展指数退避重连。
CaptureResult `errorType`:`no_translator | translator_failure | zotero_offline | timeout | extension_disconnected | cancelled | unknown`。
## 故障排查
| 现象 | 原因 / 处理 |
|---|---|
| `extension_disconnected` | Connector 扩展未加载,或 SW 未激活——在 Chrome 打开任意网页(about:blank 不算)触发 SW |
| `zotero_offline` | Zotero 桌面端没开,或 23119 端口不通——启动 Zotero 客户端 |
| `no_translator` | 该 URL 没有匹配的 translator(非学术页或需登录态已失效) |
| `translator_failure` | 站点需登录(如知网),在浏览器里重新登录后再抓 |
| WS 连不上 | 确认端口 24731 未被占用;扩展 service worker 页面无报错;查 `%LOCALAPPDATA%\zotero-claude-bridge\bridge.log` |
## 配置
环境变量:`ZCB_HOST`(默认 127.0.0.1)、`ZCB_PORT`(默认 24731)、`ZCB_LOG_LEVEL`(默认 INFO)。
扩展端开关:在 Chrome 扩展 storage 里设 `claudeBridge.enabled=false` 可禁用桥,`claudeBridge.port` 改端口(需与 server 一致)。
## 相关仓库
- 改造的 Connector 扩展:`HCLEMINI/zotero-connectors-claude-code`(基于 `zotero/zotero-connectors`)。
- 本桥与扩展通过 WS 协议契约(见 `src/zotero_claude_bridge/schemas.py` 与扩展 `src/browserExt/claude-bridge.js`)保持一致。
License: AGPL-3.0-or-later(与上游 Zotero Connectors 一致)。
This server cannot be deployed
Maintenance
ActivityMaintained
ResponsivenessSyncing