Fitbit Air Daily Planner MCP Server
MCP server that retrieves health data from Google Health API and calendar events from Google Calendar, and enables ChatGPT to create personalized wellness plans that are written to a dedicated calendar only upon user approval.
README
Fitbit Air Daily Planner
Fitbit/Pixel Watch由来のGoogle Health APIデータとGoogle Calendarの予定を組み合わせ、ChatGPTがその日のウェルネスプランを作るApps SDK + MCPアプリです。プランは確認カードで承認した場合だけ、専用Googleカレンダーへ登録されます。
単一ユーザー向けのハッカソンMVPです。医療機器ではなく、診断・治療・緊急時対応には使用できません。
なぜこの構成か
- 推論はChatGPT内のGPT-5.6が担当し、OpenAI APIを呼びません。
- サーバーはGoogle Health API v4とCalendar APIの取得・整形・書き込みだけを行います。
- 旧Google Fit REST APIは2026年末、旧Fitbit Web APIは2026年9月に停止予定のため使用しません。
- Calendarのプライマリは読み取り専用、書き込みは
GOOGLE_CALENDAR_IDで固定した専用カレンダーだけです。 - Calendarのprivate extended propertyで再試行時の重複登録を防ぎます。
- Cloudflare D1には本人プロフィールと日別集計だけを保存し、前週比と継続利用を実現します。生の心拍時系列やCalendar本文は保存しません。
- 行動目標は厚生労働省「健康づくりのための身体活動・運動ガイド2023」の成人向け推奨値を参考にし、個人差と当日の体調を優先します。
アーキテクチャ
flowchart LR
D["Fitbit / Pixel Watch"] --> H["Google Health API v4"]
C["Google Calendar primary"] --> M["Cloudflare Worker / MCP"]
H --> M
G["ChatGPT / GPT-5.6"] <-->|"Streamable HTTP"| M
G --> W["Apps SDK cards"]
W -->|"confirm"| M
M --> P["Planner-only Calendar"]
P --> N["Desktop / mobile reminders"]
MCPツール
| ツール | 動作 |
|---|---|
get_health_summary |
指定日の歩数、睡眠、心拍、欠損を取得し健康カードを表示 |
get_weekly_health_trend |
1〜14日の日別データと平均・達成日数を返す |
save_user_profile |
初回の生年月日・膝状態を保存し、年齢別目標を設定 |
list_calendar_events |
プライマリカレンダーを読み取り、場所を含む予定を返す |
create_calendar_events |
confirm:falseで下書き、カード承認後のtrueで専用カレンダーへ登録 |
ローカルセットアップ
必要環境:Node.js 20以上、npm、Google Cloudプロジェクト。
npm install
cp .dev.vars.example .dev.vars
npm test
npm run check
npm run dev
MCP URLはローカルではhttp://localhost:8787/mcp、ヘルスチェックは/healthzです。ChatGPTからの実機接続には公開HTTPS URLが必要です。
Google Cloud / OAuth
- Google CloudでGoogle Health APIとGoogle Calendar APIを有効化する。
- OAuth consent screenをExternal / Testingにし、本人をTest userへ追加する。
- Web application OAuth clientを作る。
- 次の最小スコープをData Accessへ追加する。
https://www.googleapis.com/auth/googlehealth.activity_and_fitness.readonly
https://www.googleapis.com/auth/googlehealth.health_metrics_and_measurements.readonly
https://www.googleapis.com/auth/googlehealth.sleep.readonly
https://www.googleapis.com/auth/calendar.events
- OAuth Playgroundまたは補助スクリプトで本人のrefresh tokenを取得する。
GOOGLE_CLIENT_ID=... npm run oauth:url
GOOGLE_CLIENT_ID=... GOOGLE_CLIENT_SECRET=... GOOGLE_AUTH_CODE=... npm run oauth:exchange
GOOGLE_REDIRECT_URIを省略するとOAuth Playground URLを使います。取得した秘密情報は.dev.varsまたはCloudflare Secretsにだけ保存し、コミットしません。
Testingモードのrefresh tokenは7日で失効します。AUTH_EXPIREDになったら再認可してください。未検証アプリは最大100ユーザーで、100ユーザー超または一般公開にはOAuth verificationと第三者セキュリティレビューが必要です。
環境変数
| 名前 | 種別 | 説明 |
|---|---|---|
GOOGLE_CLIENT_ID |
Secret | Google OAuth client ID |
GOOGLE_CLIENT_SECRET |
Secret | Google OAuth client secret |
GOOGLE_REFRESH_TOKEN |
Secret | 互換用token。個別tokenが未設定の場合のみ使用 |
GOOGLE_HEALTH_REFRESH_TOKEN |
Secret | Google Healthの読み取りスコープだけで認可したtoken |
GOOGLE_CALENDAR_REFRESH_TOKEN |
Secret | calendar.eventsスコープだけで認可したtoken |
GOOGLE_CALENDAR_ID |
Secret | 書き込み専用カレンダーID。primaryは禁止運用 |
MCP_SHARED_SECRET |
Secret/任意 | MCP endpointのBearer token |
DEFAULT_TIMEZONE |
Variable | 既定Asia/Tokyo |
STEPS_GOAL |
Variable | 既定8000。Google Health APIに目標APIがないためアプリ設定 |
ALLOWED_ORIGIN |
Variable | 既定https://chatgpt.com |
KNEE_STATUS |
Variable | ok / pain / unknown。既定unknown、Fitbitから推測しない |
BIRTH_DATE |
Secret/任意 | D1未使用時の単一ユーザー向け生年月日。D1プロフィールを優先 |
D1プロフィール・ログ
初回ダッシュボードで生年月日を入力すると、D1設定済み環境ではプロフィールへ保存されます。日別ログは歩数、歩数目標、睡眠分数、安静時心拍、欠損項目だけです。
npx wrangler d1 create fitbit-daily-planner
# 出力されたdatabase_idでwrangler.jsoncへDB bindingを追加
npx wrangler d1 migrations apply fitbit-daily-planner --local
追加するbinding:
"d1_databases": [{
"binding": "DB",
"database_name": "fitbit-daily-planner",
"database_id": "作成時に表示されたID"
}]
Cloudflareへのデプロイ手順(現時点では未実施)
npx wrangler login
npx wrangler secret put GOOGLE_CLIENT_ID
npx wrangler secret put GOOGLE_CLIENT_SECRET
npx wrangler secret put GOOGLE_REFRESH_TOKEN
npx wrangler secret put GOOGLE_HEALTH_REFRESH_TOKEN
npx wrangler secret put GOOGLE_CALENDAR_REFRESH_TOKEN
npx wrangler secret put GOOGLE_CALENDAR_ID
npx wrangler secret put MCP_SHARED_SECRET
npm run deploy
Cloudflare Workers Freeは小規模な単一ユーザー利用に十分ですが、無料枠超過時はリクエストが失敗する構成にし、有料機能へ自動移行しないでください。
ChatGPTへの登録と受入確認
ChatGPT BusinessのWeb版で、Workspaceの管理者/オーナーがDeveloper Modeを有効化し、デプロイしたhttps://...workers.dev/mcpをカスタムアプリとして登録します。full MCPとwrite/modify actionsはBusiness / Enterprise / EduのWeb版へbeta提供中であり、利用資格・権限・追加確認UIを実機で確認してください。
推奨プロンプト:
今日の健康サマリーと直近7日の傾向、今日の予定を確認し、無理のないウェルネスプランを作ってください。既存予定と重ねず、最初はカレンダーへ書き込まず確認カードを出してください。
確認項目:
- 健康カードに実データまたは明示的な欠損が出る。
- GPTが3つの読み取りツールを使い、プランを説明する。
confirm:falseではカレンダーに何も増えない。- カードのボタン後に専用カレンダーだけへ登録される。
- 同じ操作を再実行しても重複しない。
Scheduled Tasksからカスタムアプリを自動呼び出せるかはアカウント/ロールアウト依存の実機検証項目です。非対応でも上記1プロンプト体験を提出版の本線とします。
行動提案の基準
- 成人の既定参考値は、1日60分以上の身体活動(目安約8,000歩)、息が弾み汗をかく程度以上の運動を週60分以上、筋力トレーニングを週2〜3日です。
- 月曜〜日曜を1週間として評価し、土日、とくに日曜日は平日の不足を責めず「今週残っている実行機会」として自宅・近所の有酸素運動を提案できます。1回の運動で日々の不足が完全に帳消しになるとは説明しません。
- ジムやOWLなど外部施設・運動アプリへの誘導は行いません。移動を伴わない選択肢を優先します。
- 本人が別作業で
kneeStatus: okと設定し、当日の体調にも問題がない場合は、自重スクワット20秒+休息10秒×8セット(本編4分)を時短候補にできます。ウォームアップとクールダウンを併記し、膝の痛み・違和感または状態不明時は提案しません。 - 4分メニューを厚労省の週60分と同等換算せず、田畑式原法の効果を一般的な20/10運動へそのまま帰属させません。
制限と安全性
- ChatGPTカスタムMCPと書き込みアクションはBusiness / Enterprise / EduのWeb版が対象です。
- Apps SDK UIはWeb版で確認します。モバイルではカスタムMCPアプリを利用できない場合があります。
- Google Health APIのTesting tokenは7日で失効します。
- Google Health APIの未検証アプリは100ユーザーまでです。
- センサー未装着、同期遅延、機種差により値が欠損します。ゼロとして補完しません。
- 健康状態を断定せず、行動提案は散歩・休憩・ストレッチ・自宅での短時間運動・睡眠習慣など一般的なウェルネス支援に限定します。
- MCPは単一Googleアカウントのtokenを共有します。第三者向けに公開しないでください。
MCP_SHARED_SECRETを設定し、ChatGPT側で認証を渡せる構成にしてください。認証設定不可ならURLを公開共有しないでください。
撤去
- Cloudflare Workerを削除する。
- Google AccountのThird-party accessからアプリの権限を取り消す。
- Google CloudのOAuth credentialsと専用カレンダーを削除する。
- ローカルの
.dev.varsを削除する。
D1データベースも削除してください。保存対象はプロフィールと日別集計だけで、Durable Objectsや生データの永続コピーはありません。
提出資料
本人ログイン、OAuth認可、Developer Mode、デプロイ、実データ確認、録画・公開・提出は別チャット用の手作業票へ分離しています。本リポジトリの実装工程ではデプロイしません。
Codexの利用
Codexを使って、API廃止状況の調査、Google Health API v4への設計変更、MCPツール・Apps SDKカード・OAuth・重複防止・テスト・提出資料を一貫して作成しました。提出時にメイン開発セッションの/feedback IDを追記してください。
License
MIT
推荐服务器
Baidu Map
百度地图核心API现已全面兼容MCP协议,是国内首家兼容MCP协议的地图服务商。
Playwright MCP Server
一个模型上下文协议服务器,它使大型语言模型能够通过结构化的可访问性快照与网页进行交互,而无需视觉模型或屏幕截图。
Magic Component Platform (MCP)
一个由人工智能驱动的工具,可以从自然语言描述生成现代化的用户界面组件,并与流行的集成开发环境(IDE)集成,从而简化用户界面开发流程。
Audiense Insights MCP Server
通过模型上下文协议启用与 Audiense Insights 账户的交互,从而促进营销洞察和受众数据的提取和分析,包括人口统计信息、行为和影响者互动。
VeyraX
一个单一的 MCP 工具,连接你所有喜爱的工具:Gmail、日历以及其他 40 多个工具。
Kagi MCP Server
一个 MCP 服务器,集成了 Kagi 搜索功能和 Claude AI,使 Claude 能够在回答需要最新信息的问题时执行实时网络搜索。
graphlit-mcp-server
模型上下文协议 (MCP) 服务器实现了 MCP 客户端与 Graphlit 服务之间的集成。 除了网络爬取之外,还可以将任何内容(从 Slack 到 Gmail 再到播客订阅源)导入到 Graphlit 项目中,然后从 MCP 客户端检索相关内容。
e2b-mcp-server
使用 MCP 通过 e2b 运行代码。
Neon MCP Server
用于与 Neon 管理 API 和数据库交互的 MCP 服务器
Exa MCP Server
模型上下文协议(MCP)服务器允许像 Claude 这样的 AI 助手使用 Exa AI 搜索 API 进行网络搜索。这种设置允许 AI 模型以安全和受控的方式获取实时的网络信息。