内容
# mcp-server-whoop
[](https://www.npmjs.com/package/mcp-server-whoop)
[](https://github.com/Yadheedhya06/mcp-server-whoop/actions/workflows/ci.yml)
[](https://github.com/Yadheedhya06/mcp-server-whoop/actions/workflows/security.yml)
[](https://scorecard.dev/viewer/?uri=github.com/Yadheedhya06/mcp-server-whoop)
[](LICENSE)
一个本地优先、只读的 [Model Context Protocol](https://modelcontextprotocol.io/) 服务器,用于 WHOOP。它为兼容 MCP 的 AI 客户端提供紧凑的恢复、睡眠、压力、心率变异性、心率、锻炼和身体测量信号,而无需通过托管的第三方发送您的 WHOOP 凭证。
## 为什么使用这个服务器
- 标准的 MCP 通过 stdio,可被任何支持本地 MCP 服务器的客户端使用
- 每个用户拥有自己的 WHOOP 开发者应用程序的本地 WHOOP OAuth 流
- 访问和旋转刷新令牌保留在用户的机器上
- 五个专注的只读工具,而不是嘈杂的 API 转储
- 每条记录的本地时间戳,以便旅行不会改变睡眠或锻炼日期
- 明确的 `processing` 状态,在新睡眠待处理时,不会替换旧恢复
- 人类规模的小时、分钟、卡路里和心率区分钟
- 工具输出中没有原始标识符、OAuth 机密或原始连续心率声明
- 没有托管的中继、遥测、数据库、通用 HTTP 工具、原始 SQL 或安装生命周期脚本
- 可复制的 tarball 安全审计、CycloneDX SBOM、CodeQL、Gitleaks、依赖项审查和 OpenSSF 评分卡
> 这是一个独立的社区项目。它与 WHOOP 无关,也未得到 WHOOP 的认可。WHOOP 数据是有用的教练背景,而不是医疗建议。
## 要求
- Node.js 18 或更新版本
- 一个 WHOOP 账户
- 在 [WHOOP 开发者仪表板](https://developer.whoop.com/dashboard/) 上申请一个免费应用程序
- 一个兼容 MCP 的 AI 客户端
## 快速入门
1. 创建一个 WHOOP 开发者应用程序,并注册 `http://127.0.0.1:8765/callback`。
2. 启用下面列出的五个读取范围和 `offline`。
3. 在终端中运行 `npx -y mcp-server-whoop@0.2.1 auth` 并批准 WHOOP 访问。
4. 运行 `npx -y mcp-server-whoop@0.2.1 status` 以确认本地授权存在。
5. 在 AI 客户端的 MCP 配置中添加 `npx -y mcp-server-whoop@0.2.1` 的 stdio 命令。
6. 重启或重新加载客户端,然后询问:`使用 WHOOP 总结我过去 7 天的恢复和睡眠情况。`
授权命令和 AI 客户端必须在同一操作系统用户下运行,或者两者都必须将 `WHOOP_CREDENTIALS_FILE` 设置为同一私有文件。该软件包永远不会要求您将 WHOOP 令牌粘贴到 AI 对话中。
文档默认固定一个确切的已审查版本。只有当您明确希望客户端在不首先审查的情况下跟随未来版本时,才使用 `@latest`。
## 1. 创建您的 WHOOP 应用程序
在 WHOOP 开发者仪表板中创建一个应用程序,并注册此确切的重定向 URL:
```text
http://127.0.0.1:8765/callback
```
启用这些范围:
```text
offline
read:recovery
read:cycles
read:sleep
read:workout
read:body_measurement
```
`offline` 是必需的,因为 WHOOP 访问令牌会过期,而 WHOOP 会旋转刷新令牌。
## 2. 在本地授权
运行:
```bash
npx -y mcp-server-whoop@0.2.1 auth
```
该命令提示输入您的 WHOOP 客户端 ID 并掩盖客户端机密,在浏览器中打开 WHOOP 同意,验证 OAuth 状态,并本地保存生成的授权。
凭证存储在:
```text
~/.config/mcp-server-whoop/credentials.json
```
在 Linux 和 macOS 上,每个路径祖先在被使用之前都会被检查,直接目录由当前用户拥有,模式为 `0700`,文件是一个单一链接的当前用户拥有普通文件,模式为 `0600`。只有当每个祖先都受信任并且不是符号链接时,才使用 `WHOOP_CREDENTIALS_FILE` 覆盖路径。
本机 Windows 上的持久 OAuth 凭证故意关闭。Node.js 文件模式不强制执行私有 Windows ACL,其标准文件 API 无法保证重新解析安全凭证写入。本地 Windows 用户可以通过 MCP 进程环境提供短期的 `WHOOP_ACCESS_TOKEN`,但自动授权和刷新令牌持久化需要 WSL、Linux 或 macOS,直到本机凭证后端可用。
对于无头环境,在运行 `auth` 之前,请将 `WHOOP_CLIENT_ID`、`WHOOP_CLIENT_SECRET` 和可选的 `WHOOP_REDIRECT_URI` 作为环境变量提供。
OAuth 回调仍然需要访问运行 `auth` 的机器。当通过 SSH 授权时,首先从工作站创建一个循环回路隧道:
```bash
ssh -L 8765:127.0.0.1:8765 user@your-server
```
然后在 SSH 会话中运行 `auth`,并在工作站浏览器中打开其打印的 WHOOP URL。不要将客户端机密作为命令行参数传递,因为 shell 历史记录和进程列表可能会暴露它。
检查设置而不显示机密:
```bash
npx -y mcp-server-whoop@0.2.1 status
```
删除本地授权:
```bash
npx -y mcp-server-whoop@0.2.1 logout
```
在不再使用集成时,也建议在 WHOOP 账户设置中撤销访问权限。
## 3. 添加到 AI 客户端
### Claude Desktop
在 Claude Desktop 的配置中添加以下内容到 `mcpServers` 下,然后完全重启 Claude Desktop:
```json
{
"mcpServers": {
"whoop": {
"command": "npx",
"args": ["-y", "mcp-server-whoop@0.2.1"]
}
}
}
```
### Claude Code
```bash
claude mcp add --transport stdio whoop -- npx -y mcp-server-whoop@0.2.1
```
### Cursor、Windsurf、Gemini Code Assist 等 `mcpServers` 客户端
将服务器添加到客户端的 MCP JSON 中。Gemini Code Assist 使用 `~/.gemini/settings.json`;其他客户端选择自己的设置路径。
```json
{
"mcpServers": {
"whoop": {
"command": "npx",
"args": ["-y", "mcp-server-whoop@0.2.1"]
}
}
}
```
### VS Code
为项目创建 `.vscode/mcp.json`,或使用 VS Code 的 **MCP: 添加服务器** 命令:
```json
{
"servers": {
"whoop": {
"type": "stdio",
"command": "npx",
"args": ["-y", "mcp-server-whoop@0.2.1"]
}
}
}
```
### Codex
运行:
```bash
codex mcp add whoop -- npx -y mcp-server-whoop@0.2.1
```
或将以下内容添加到 `~/.codex/config.toml`:
```toml
[mcp_servers.whoop]
command = "npx"
args = ["-y", "mcp-server-whoop@0.2.1"]
```
### ChatGPT
本地 Codex 和 ChatGPT 桌面客户端支持 stdio,可以使用上面的 Codex 配置。ChatGPT 网页不会在您的计算机上启动命令;它需要一个单独的安全远程桥或隧道和一个工作区插件。该存储库故意不提供或操作公共健康数据中继。
客户端菜单和配置路径会随时间变化。如果客户端支持标准的本地 stdio MCP,则可移植的值始终是:
```text
command: npx
arguments: -y mcp-server-whoop@0.2.1
```
## 确认连接
重启客户端后,确认它恰好发现这五个工具:
```text
whoop_latest_overview
whoop_recovery_history
whoop_sleep_history
whoop_cycle_strain_history
whoop_workout_history
```
有用提示:
- `使用 WHOOP 查看今天的恢复、最新的睡眠、当前的压力和最新的锻炼。`
- `比较过去 14 天我的恢复、HRV 和静息心率。`
- `显示我过去 7 天的睡眠,包括小睡,并标记任何仍在处理的内容。`
- `总结过去 30 天我的锻炼压力和心率区。`
- `将 WHOOP 作为今天训练的参考,但不要将其视为医疗建议。`
模型决定何时调用工具,因此当您想要实时数据而不是通用答案时,请明确说 `使用 WHOOP`。
## 工具
| 工具 | 目的 |
|---|---|
| `whoop_latest_overview` | 当前的教练快照,带有待处理数据保护 |
| `whoop_recovery_history` | 恢复、HRV、静息心率、SpO2 和皮肤温度趋势 |
| `whoop_sleep_history` | 主要睡眠和可选小睡、阶段、需求、质量和时间 |
| `whoop_cycle_strain_history` | 每日压力、卡路里和平均/最大心率 |
| `whoop_workout_history` | 运动、持续时间、压力、心率、卡路里、距离和区域分钟 |
所有工具都标记为只读、非破坏性和幂等。
### 为什么故意只有五个工具?
对于健康数据的 MCP,工具数量的增加也意味着能力表面的增加。该服务器将身份验证放在代理之外,并仅为模型提供它需要的五个健康读取能力。
它故意具有:
- 没有 WHOOP 写、撤销、令牌管理或授权码工具
- 没有个人资料/电子邮件/名称范围
- 没有原始记录、原始 ID、任意端点、SQL、文件或 shell 工具
- 没有托管的 OAuth 中继、遥测服务、健康数据缓存或数据库
- 在最新睡眠仍在处理时,没有旧恢复的备用
目标不是最大化 WHOOP API 覆盖范围。这是用于恢复感知 AI 的最小实用权限边界。
## 数据语义
WHOOP 返回绝对时间戳和睡眠、周期和锻炼记录的 `timezone_offset`。该服务器应用每个记录的偏移量,并仅返回已经转换的本地时间戳,例如:
```text
2026-07-07 18:02:22 +04:00
```
它不将机器的当前时区应用于历史记录。
WHOOP 公开活动类型和锻炼运动,但其公共 API 不指示锻炼是否自动检测或手动启动。该服务器不会猜测。
当最新的主要睡眠仍为 `PENDING_SCORE` 时,最新的概览返回:
```json
{
"status": {
"state": "waiting_for_whoop",
"current_recovery_available": false
},
"recovery": null
}
```
永远不会将较旧的恢复作为当前呈现。
## 环境变量
| 变量 | 目的 |
|---|---|
| `WHOOP_CLIENT_ID` | WHOOP OAuth 客户端 ID |
| `WHOOP_CLIENT_SECRET` | WHOOP OAuth 客户端机密 |
| `WHOOP_REDIRECT_URI` | OAuth 回调,默认为 `http://127.0.0.1:8765/callback` |
| `WHOOP_CREDENTIALS_FILE` | 覆盖本地凭证文件路径 |
| `WHOOP_ACCESS_TOKEN` | 可选的短期访问令牌覆盖 |
| `WHOOP_REFRESH_TOKEN` | 可选的刷新令牌覆盖 |
| `WHOOP_TOKEN_EXPIRES_AT` | 可选的 ISO 令牌过期覆盖 |
`WHOOP_CLIENT_ID`、`WHOOP_CLIENT_SECRET` 和 `WHOOP_REDIRECT_URI` 的客户端配置覆盖文件值。令牌环境变量可以引导无头设置,但一旦刷新令牌旋转,凭证文件中保存的新令牌将优先使用。不要将机密直接放在命令行参数中或提交到源代码管理中。
## 故障排除
### `缺少 WHOOP ...`
以启动 AI 客户端的相同 OS 用户身份运行 `npx -y mcp-server-whoop@0.2.1 status`。如果凭证位于其他位置,请在客户端的 MCP 环境中设置 `WHOOP_CREDENTIALS_FILE`。
### WHOOP 报告重定向不匹配
开发者仪表板中的重定向和此软件包使用的值必须完全匹配。默认值为 `http://127.0.0.1:8765/callback`,包括方案、主机、端口和路径。
### 浏览器未打开
复制终端中打印的授权 URL 并手动打开它。回调监听器在五分钟后过期;如果需要,请重新运行 `auth`。
### 端口 `8765` 已被占用
注册另一个循环回路 URL,例如 `http://127.0.0.1:9876/callback`,将 `WHOOP_REDIRECT_URI` 设置为该确切值,然后重新运行 `auth`。
### 恢复为 `null`
检查返回的 `status.state`。如果它是 `waiting_for_whoop` 或 `waiting_for_recovery`,则 WHOOP 尚未完成新睡眠的评分。该服务器故意拒绝将较旧的恢复标记为当前;请在 WHOOP 完成处理后重试。
### 客户端未显示工具
在终端中运行 `npx -y mcp-server-whoop@0.2.1 --help` 以验证 Node.js 和 npm 可以启动软件包,然后重启 AI 客户端并检查其 MCP 日志。不要交互式地运行裸服务器以检查输出:stdio 保留用于 MCP 协议消息。
## 开发
```bash
git clone git@github.com:Yadheedhya06/mcp-server-whoop.git
cd mcp-server-whoop
npm ci --ignore-scripts
npm run check
```
运行本地源服务器:
```bash
npm run dev
```
构建并检查确切的 npm 工件:
```bash
npm pack --dry-run
```
## 隐私和安全
该项目发布证据,而不是声称任何软件包都是完全安全的。请参阅完整的安全策略和可复制的安全证据。
- 每个用户都拥有自己的 WHOOP 开发者应用程序和 OAuth 授权。
- 凭证保留在本地,永远不会通过 MCP 工具返回。
- 软件包不提供 WHOOP 写、通用网络、shell、文件系统或原始 API 直通工具。
- 在受支持的 POSIX 存储上,检查凭证文件和每个祖先的符号链接、不安全的所有权或权限、超大输入和意外字段。刷新轮换使用心跳租约,不信任 PID、独家临时文件、原子替换、写入后验证和磁盘同步。本地 Windows 持久性关闭。
- WHOOP 和 OAuth 响应是大小有限且结构验证的;提供者响应正文永远不会复制到 MCP 错误中。
- 直接依赖项使用确切版本。只有两个直接运行时依赖项,没有软件包安装生命周期脚本。
- CI 在 Node 18、20、22 和 24 上运行完整测试套件,添加 macOS 和 Windows 平台安全作业,审计源代码和确切的编译 npm 运行时,验证 npm 注册表签名,并生成 CycloneDX SBOM。
- 独立工作流运行 CodeQL、Gitleaks、依赖项审查和 OpenSSF 评分卡。
- 发布工作流打包一次,并通过 npm Trusted Publishing 与 Sigstore 原始证明发布。GitHub 将其与 CycloneDX SBOM 分别证明;不使用长期 npm 令牌。
这些控制措施降低了风险,但它们不是付费渗透测试或保证。限制在 `SECURITY-EVIDENCE.md` 中明确记录。
## 许可证
MIT