mcp-fitbod
目录
概述 · 安装 · 配置 · 工具 · 身份验证 · 重要发现 · 限制 · 架构 · 法律
Related MCP server: tonal-mcp-cloudflare-workers
概述
mcp-fitbod 将 Fitbod 账户置于一个基于 stdio 的 MCP 服务器之后,因此任何 MCP 客户端都可以直接使用你的训练数据。它横跨十个后端服务,而非仅仅一个端点:
服务 | 包含内容 | 工具 |
| 训练计划、健身房、器械、生成器配置、个人资料、训练历史 | 36 |
| 身体成分时间序列、力量评分、连续打卡、百分位 | 11 |
| 训练生成器,包括一个由 LLM 驱动的变体 | 4 |
| 具有持久记忆的 AI 教练会话 | 5 |
| 公共健身房目录和 Places 搜索 | 3 |
| AI 聊天后端 | 1 |
| 应用内消息、Strava、订阅状态 | 4 |
| 登录和按服务签发令牌 | 认证层 |
最有用的部分是 pyserve。大多数集成都是在应用之外编写训练计划;而本服务器会直接调用生成器本身,返回包含动作选择、组数、次数、负重和休息时间的完整训练会话,然后根据你实际拥有的器械对结果进行过滤,并对任何你无法完成的动作请求替换。
亮点
每个写入工具默认设置
dry_run=True,并返回它将发送的确切载荷,而不会改动账户。包含约 1,400 个动作的离线语料库意味着目录查询、健身房过滤和肌肉映射无需任何网络调用。
build_routine会在写入之前根据你的健身房验证每一个动作,并在部分失败时删除该训练计划,从而不会留下半成品。分析功能(总吨位、各肌群训练量、估算 1RM、停滞不前的动作)位于纯函数中,不依赖网络,并针对固定测试数据进行了单元测试。
令牌签发、
401时刷新、速率限制、分页以及临时挑战重试均在客户端内部处理。
安装
需要 Python 3.10 或更高版本。
git clone https://github.com/Muno459/mcp-fitbod
cd mcp-fitbod
pip install -e ".[dev]"只需认证一次。刷新令牌的有效期约为一年,并且只有该令牌会被持久化保存。
FITBOD_EMAIL='you@example.com' FITBOD_PASSWORD='...' python -m fitbod.auth从你自己的 Fitbod 安装中构建离线动作语料库。解压 APK,然后将构建器指向其 res/raw 目录。
python build_reference.py --apk-res /path/to/fitbod/res/raw描述你的健身房,以便工具能够筛选出可执行的动作。
cp data/gym-profile.example.json data/gym-profile.json
$EDITOR data/gym-profile.json验证,然后运行。
python -m pytest tests/ -q # offline: parsing and analysis
python smoke_test.py # live: every tool, writes are dry-run
python server.py配置
通过 stdio 将服务器注册到任何 MCP 客户端:
{
"mcpServers": {
"fitbod": {
"command": "python",
"args": ["/absolute/path/to/mcp-fitbod/server.py"]
}
}
}变量 | 用途 |
| 仅由 |
| 仅由 |
| 直接提供刷新令牌,而不使用凭据文件 |
凭据保存在 .fitbod-credentials.json 中,仅所有者可读且已被 gitignore。该文件只包含刷新令牌,别无其他。你的密码永远不会写入磁盘,也永远不会被记录。要撤销访问权限,请更改你的密码。
data/gym-profile.json 将你拥有的器械映射到 Fitbod 的 78 种器械类型,包括你可用的确切哑铃和杠铃片增量,从而确保开出的负重是你实际能够组合出来的。从 data/gym-profile.example.json 开始,并使用 preview_inventory_mapping 检查你的名称能否正确解析。
工具
共 97 个工具,分布在十二个模块中。每个写入工具都接受 dry_run。
工具 | 描述 |
| 已记录的训练,最新的在前 |
| 单个训练的完整详情,每一组都已展开 |
| 某个动作的每一组已记录数据,含估算 1RM |
| 每个肌群的有效组数和总吨位 |
| 最佳估算 1RM 未再提升的动作 |
| 一次调用即可获得总量、各肌群训练量和停滞动作 |
| 通过服务器自身的聚合获取训练总次数 |
| 来自个人资料的身体指标 |
| 将一次已完成的训练记录到历史中 |
| 编辑历史中已有的训练 |
估算 1RM 采用 Epley 公式。热身组不计入有效组数和总吨位。空窗口会返回一条说明性的 note,而不是一个光秃秃的零。
工具 | 描述 |
| 让 Fitbod 自己的引擎生成一次训练会话 |
| 生成后,将指定的动作替换掉 |
| 关于已生成训练的自由文本提问 |
| 生成器的接口及其已知约束 |
有三个引擎可供选择:foundational_model、algo_direct_client 和
algo_llamabod。结果会根据你的健身房进行后置过滤,任何无法完成的动作都会通过
exercise_replacement 自动替换。
工具 | 描述 |
| 账户上的健身房及器械数量 |
| 当前关联到某个健身房的器械 |
| 你的库存如何映射到 Fitbod 器械 id |
| 根据你的库存创建一个配置好的健身房 |
| 挂载或移除一种器械类型 |
| 声明某一种类型存在哪些具体重量 |
| 应用已记录的哑铃和杠铃片增量 |
| 删除一个健身房 |
工具 | 描述 |
| 目标、分化、经验、每周天数、超级组、热身、时长 |
| 训练阶段及其重点动作 |
| 每个动作的系数,用于影响选择偏向 |
工具 | 描述 |
| 一次调用创建完整训练计划,支持回滚 |
| 读取已保存的模板 |
| 模板生命周期 |
| 添加一个规定动作 |
| 创建一个动作组容器 |
| 定义 Fitbod 未建模的动作 |
工具 | 描述 |
| 当前成分及各指标的完整历史 |
| 随时间变化的瘦体重和体重,含变化量 |
| 各肌肉相对于人群的评分 |
| 某个动作在所有人中的排名百分位 |
| 连续打卡、每周次数、训练量目标 |
| 指标目录及其数字 id |
| 写入和删除读数 |
体重、瘦体重、脂肪量、体脂率、BMI、BMR 以及七项围度均有完整时间序列可用,数据来源于 Apple Health 或 Health Connect。
动作目录:find_exercises exercise_detail search_exercises_live
exercise_details_live list_equipment muscle_groups warm_start_lookup
onboarding_one_rep_maxes seed_one_rep_max api_surface gym_profile
个人资料:get_profile update_profile add_injury list_injuries
delete_injury rate_exercise list_exercise_ratings registered_devices
app_config selected_cardio add_selected_cardio remove_selected_cardio
selected_resistance_bands
教练与聊天:coach_ask coach_sessions coach_new_session
coach_memories coach_session_stats chat
分析:exercise_analytics exercise_benchmarks workout_achievements
其他服务:service_health subscription_status list_blimps
dismiss_blimp strava_connection list_public_gyms public_gym_equipment
search_places
营养:nutrition_targets todays_targets recalculate_targets
cut_progress
逃生舱:raw_get 和 metros_raw_get,两者均为只读,并带有路径
校验。
身份验证
分为三步,每个微服务都从一个长期有效的刷新令牌(refresh token)自行铸造自己的短期令牌:
POST gate-keeper.fitbod.me/users/login {"user":{"email","password"}}
-> 201, refresh JWT in the Authorization RESPONSE header, exp about 1 year
POST <service>.fitbod.me/access_token {"refresh_token":"<raw jwt>"}
-> 201 {"access_token": ...}, aud=<service>.prod.fitbod.me, about 24h
Authorization: Bearer <access_token> -> https://<service>.fitbod.me/...客户端会将访问令牌缓存 23 小时,并在收到 401 时透明地重新铸造。注意各服务之间的不一致:nautilus 要求在请求体中包含 refresh_token,而 prism、blimp 和 metros 也接受将其放在请求头中。
需要形如浏览器的 User-Agent,因为已知的机器人代理(如 curl/*)会在请求到达源站之前就被边缘节点拒绝。
重要发现
这些是需要花费实际时间才能摸索出来的行为,记录下来以免重复踩坑。
两套序列化机制并存。 JSON:API 属性使用 snake_case,但内嵌文档会原样使用源属性名,除非有显式注解覆盖。在 individual_sets 内部,isWarmup 和 restTime 保持 camelCase,而 _id、_created_at 和 is_amrap 则带有覆盖。混淆这两套机制会静默丢失所有字段。
有些映射无法凭猜测得知。 workoutConfigId 序列化为 default_workout_config_id,circuitsEnabled 序列化为 supersets_enabled,而 algorithmCoefficient 序列化为 algorithm_coeffecient——这个拼写错误出现在线上数据中。
已记录组不使用资源 id。 它们通过 exercise_external_resource_id 引用动作,这是一个不同的编号。Leg Press 的 id=291,但 external_resource_id=218。
POST 和 PUT 对 id 的要求不一致。 POST workout_data 拒绝任何 id(data.attributes.id should be type integer_id),而 PUT workout_data/{id} 要求 data.id 与路径匹配。
关系(relationships)与属性(attributes)之别。 gym_id 和 equipment_id 可读但不可写。创建 gym_equipment 记录需要使用 JSON:API 的关系(relationships),而不是属性。
枚举值是固定的,且顺序很重要。
FitnessGoal 0 GENERAL_FITNESS 1 STRENGTH_TRAINING 2 MUSCLE_TONE
3 BODYBUILDING 4 POWERLIFTING 5 OLYMPICWEIGHTLIFTING
MuscleSplit 0 FRESH_MUSCLE_GROUPS 1 UPPER_LOWER 2 FULL_BODY 3 PPL
ExperienceLevel 0 BEGINNER 1 INTERMEDIATE 2 EXPERT
WorkoutVariability 1 MORE_CONSISTENCY 3 SUGGESTED 5 MORE_VARIABILITY
StrengthAggregate push, pull, lower (there is no upper and no core)
ExerciseRating like, dislike, exclude (lowercase; uppercase returns 500)生成器的怪癖。 algo_versions 是必填项,但其中的每个字段都可以为 null。空的 user_equipment 或 muscle_usages_from_client 会返回 500。exercise_replacement 需要将训练回显为 current_workout,并且 exercise_ids_to_replace 中的每个 id 都必须出现在其中。生成器不会严格遵循 user_equipment,所以始终要做后置过滤。
突发请求会被质询。 带有 HTML 响应体的 403 是暂时性的,大约 10 到 30 秒内就会解除。客户端会重试,而不是将其作为认证错误抛出——尽管乍一看它很像认证错误。
时长单位是秒。 已记录训练中的 duration 不是分钟,这一点很容易被忽略,直到一次 65 分钟的训练显示为 3908。
已知限制
已针对订阅账户,并尝试了各种载荷形态进行确认:
端点 | 行为 |
| 所有形态都返回 |
|
|
| 任何值(包括 null)都会返回 |
教练会话 | 无法删除( |
根本没有营养 API。营养工具会在本地存储目标,并根据实时身体成分数据推导出这些目标。
架构
server.py thin entrypoint, registers tool modules
fitbod/
client.py auth chain, rate limiting, retry, pagination
auth.py python -m fitbod.auth
schemas.py dataclass parsers for both serialisation regimes
analysis.py volume, stalled lifts, 1RM. Pure, network free
reference.py offline corpus, dual id index, gym filtering
tools/ read, catalogue, gym, config, program, profile,
metrics, generate, services, coach, extras, nutrition
tests/ offline tests over recorded fixtures
docs/
API-MAP.md 145 endpoints, 365 request and response models
SCHEMAS.md field level schemas with exact wire names
build_reference.py builds the offline corpus from an extracted APK
smoke_test.py exercises all 97 tools live, writes dry-run by default请求在客户端被限速为每秒 6 个,突发上限为 10 个。这是一个礼貌性预算,而非实测到的上限:50 个并发请求可持续达到每秒约 32 个,且没有出现任何 429,任何响应上也没有速率限制头。如果你需要更高吞吐量,还有余量。
动作语料库使用双索引作为键,因为已记录组和目录条目使用不同的 id 空间。reference.by_id() 和 reference.by_external_id() 正是为此而同时存在。
文档
文件 | 内容 |
| 完整的接口面:12 个接口中共 145 个端点声明,以及 365 个经传递解析的请求和响应模型 |
| 字段级模式,包含精确的线上名称、类型和必填标志 |
| 尚未解决的问题及其原因 |
动作目录
build_reference.py 会从解压后的 Fitbod APK 的 res/raw 目录构建 data/exercise-reference.json:大约 1,400 个带有文字说明的动作、78 种器械类型、肌群映射和器械重量表。这些内容归 Fitbod 所有,因此不在此分发。请从你自己的安装中构建。
法律声明
本项目使用未记录的 API,极有可能违反 Fitbod 的服务条款,尽管它只会访问你自己的账户,并且不规避付费。它的存在是为了与你自己的训练数据进行个人互操作。请仅在你自己的账户上使用,风险自负,且不要将其指向任何其他人的账户。
横幅中的六边形标志是一幅原创绘图,灵感来自 Fitbod 的视觉形象,并非其商标;本项目与 Fitbod 没有任何关联、背书或联系。
许可证
MIT
This server cannot be deployed
Maintenance
Related MCP Connectors
Read your workouts, history, and stats; create and schedule new workouts. Writes are additive only.
Access COROS activity, training and health data, and manage training plans and workouts.
Read-only access to your PumpX workout log: sessions, lift history, PRs, routines, measurements.
Read athletes, workouts, scores and movements; change an athlete's name or email in SugarWOD.
Related MCP Servers
- FlicenseNot gradedqualityCmaintenanceEnables reading Hevy workout data and creating workout routines and logged workouts through Hevy's public API.2,700 npm-
- AlicenseNot gradedqualityCmaintenanceEnables querying a Tonal fitness account for workout history with per-set weights, muscle readiness, strength scores, and lifetime stats through a remote MCP endpoint.MIT
- AlicenseNot gradedqualityBmaintenanceEnables AI agents to access and manage fitness programs, exercise catalog, workout resources, activity metrics, journaled plan edits, and change tracking through authenticated tools.2 npmMIT
- AlicenseNot gradedqualityBmaintenanceEnables conversational logging and retrieval of workouts, sets, weigh-ins, meals, goals, plans, and progress photos through MCP-capable AI clients, with authenticated per-user storage and export/query capabilities.ISC