gdocs
gdocs — 面向 Claude Code 的 Google Docs 审阅循环
一个 MCP 服务器,让 Claude Code 可以读取一份 Google 文档及其评论线程,并把修改写回同一 URL 下的同一篇文档。
它是为这种循环而构建的:仓库中的 Markdown 是事实来源,Google Docs 只是审阅界面。它省去了复制粘贴的往返:不用把草稿粘贴到 Docs,也不用把审阅者的评论粘贴回终端。
它安装到用户作用域,因此适用于每个项目。
要求
Node 18+
claudeCLI一个 Google 账号,以及在 Google Cloud Console 中大约 10 分钟
安装
git clone https://github.com/uma-victor1/gdocs-mcp.git
cd gdocs-mcp
./install.sh这会安装依赖、验证服务器能启动,并把它注册到 Claude Code 的用户作用域。然后你再自行完成下面的两个凭据步骤。
1. Google Cloud,只做一次
启用 Google Docs API 和 Google Drive API(API 和服务 > 媒体库)
OAuth 同意屏幕:个人账号用外部用户类型即可。在 受众群体 下把你自己的地址添加为 测试用户——跳过这一步是同意失败的最常见原因。
凭据 > 创建凭据 > OAuth 客户端 ID > 桌面应用 > 下载 JSON
把它保存为
~/.config/gdocs-mcp/credentials.json
把凭据放在任何仓库之外是有意为之,所以 git add -A 永远不可能把它们提交进去。
2. 授权,只做一次
npm run authGoogle 会警告该应用未经验证。对一个只有一个用户的应用来说这是正常现象:高级选项 > 继续前往…(不安全)。刷新令牌会写入 ~/.config/gdocs-mcp/token.json,权限为 0600。
重启 Claude Code,然后用 claude mcp list 确认。
每 7 天重新授权,以及原因
在同意屏幕处于测试状态期间,Google 会让刷新令牌每 7 天过期一次。这是外部应用处于测试状态时有记载的行为,不是 bug,而且对于这套作用域集合来说也绕不开:auth/drive 是受限作用域,带受限作用域发布到生产环境需要 CASA 安全评估——对一人工具而言不值得。
所以大约每周会有一次工具调用因为“授权已过期”失败。修复方法:
npm run auth这可以只花十五秒就能完成。如果你有 Google Workspace 账号,可以完全避免这种情况。在该组织下创建 Cloud 项目,并把同意屏幕的用户类型设为内部。内部应用没有 7 天过期,也没有测试用户列表。
工具
表格如下。
工具 | 含义 |
| 按标题在 Drive 中搜索文档 |
| 正文以 Markdown 返回 + 评论线程,每条线程附有锚定文本 |
| 只返回评论线程——相当于“有没有新评论?”的廉价检查 |
| 就地精确查找替换;保留评论锚点 |
| 在末尾追加一个带样式的段落(标题级别、字号、颜色、粗体/斜体);只追加,不改写,保留锚点 |
| 用本地文件替换整个正文;需要 |
| 在评论线程上发布回复 |
| 用一条结束语解决(resolve)评论线程 |
| 用 Markdown 文件创建新文档——每篇文档一次 |
所有工具可以接受文档 URL 或一个纯 fileId。
评论锚点的权衡
Google 把每条评论锚定到一段文本上。重写那段文本,评论线程就会脱锚或自动解决。所以:
小修改 →
replace_text。 锚点仍然保留;审阅者仍然保留上下文。结构性的重写 →
push_markdown。 更快,但肯定有疑虑。它会先报告原来有多少条未解决的线程,于是损失是可见的而不是无声无息的。是加而不是改 →
append_text。 它只会往末尾插入,所以任何现有的文本跨度都不会移动,锚点也不会被破坏。重写之前先回复。
reply_comment会留下为什么要这样改的记录。
为什么用这个,而不是现成的服务器
一个持有 Docs OAuth 令牌的 MCP 服务器,可以读取并改写该账号中的任何文档。目前没有第一方 Google 或 Anthropic 的 Docs MCP 服务器;所有发布的都是第三方个人发布者的包。这个项目是大约 250 行,基于 Anthropic 的 MCP SDK 和 Google 自己的客户端库——足够小,你可以在信任之前通读一遍。
只读模式
claude mcp remove gdocs -s user
claude mcp add gdocs -s user -e GDOCS_MCP_READONLY=1 -- node "$PWD/server.mjs"读取功能仍然可用;写工具会拒绝执行。当别人拥有文档时很有用。
故障排查
症状 | 修复 |
“尚未授权” | 运行 |
| 登录的地址不是已批准的测试用户。在 OAuth 同意屏幕 > 受众群体 > 测试用户 下添加它,保存后重试 |
大约一周后“授权已过期” | 测试模式下的预期行为。运行 |
| 在这个 Cloud 项目上启用 Docs API 和 Drive API |
“没有刷新令牌” | 到 https://myaccount.google.com/permissions 撤销授权,然后重新运行 |
Claude Code 中找不到服务器 | 运行 |
文档导出为纯文本 | 文档里有 Google 无法渲染成 Markdown 的内容;但内容仍会返回 |
任何时候都可以用 npm run smoke 独立验证服务器。
要在不经过 Claude Code 的情况下也执行某个工具:
node call.mjs read_comments '{"doc":"https://docs.google.com/document/d/FILEID/edit"}'撤销授权
到 https://myaccount.google.com/permissions 撤销,然后删除 ~/.config/gdocs-mcp/token.json。
布局
server.mjs the nine tools
google.mjs auth + Drive/Docs clients; credential paths
auth.mjs one-time interactive OAuth (npm run auth)
smoke.mjs starts the server, lists tools (npm run smoke)
call.mjs invoke one tool from the shell, for debugging
install.sh deps, verify, register at user scope
docs/guide.html the setup walkthrough as a standalone page许可证
MIT。参见 LICENSE。
This server cannot be installed
Maintenance
Resources
Unclaimed servers have limited discoverability.
Looking for Admin?
If you are the server author, to access and configure the admin panel.
Related MCP Connectors
Connect Claude to Fathom meeting recordings, transcripts, and summaries
Read, edit, publish, and preview your pepita websites from Claude.
WHOOP recovery, strain, sleep and workouts in Claude via official WHOOP OAuth. Free, open source.
Latest Blog Posts
- Who's Calling? MCP Hosts Are an Identity Blind Spot (And the Spec Knows It)By Om-Shree-0709 on .mcpAgent IdentityOAuth 2.1
- Your AI Chatbot Just Exposed Your CEO's Salary to an InternBy Om-Shree-0709 on .Agent IdentityMCP SecurityOAuth Delegation
- Why MCP Servers Need Execution Sandboxing (And Why Your Current Stack Isn't Enough)By Om-Shree-0709 on .Agentic AiPrompt InjectionWebAssembly
MCP directory API
We provide all the information about MCP servers via our MCP API.
curl -X GET 'https://glama.ai/api/mcp/v1/servers/uma-victor1/gdocs-mcp'
If you have feedback or need assistance with the MCP directory API, please join our Discord server