Garmin Coach MCP
by javipaur
README.md
# 🏃 Garmin Coach MCP
**Lo que tu reloj sabe hoy, trabaja para ti esta noche.**
Un puente autohospedado entre **Garmin Connect** y tu asistente de IA (Claude, Cursor, VS Code, móvil…). Conectas tu cuenta Garmin una vez y conversas con tus propios números: VFC, carga de entrenamiento, sueño, ritmos y planes. Incluye un **panel web multi-usuario** para gestionar un club entero de corredores.
---
## ✨ Qué hace
- **Habla con tus números** — pregunta en lenguaje normal: *«¿estoy sobreentrenando?»*, *«¿qué ritmo en Z3?»*, *«saca una ruta de 12 km desde casa»*.
- **120+ herramientas MCP** — `get_daily_summary`, `get_hrv_data`, `detect_fatigue_risk`, `plan_this_week`, `parse_training_pdf`, `calculate_pace_zones`, `route_from_home`, `get_race_predictions` y muchas más.
- **Fatiga real, no clichés** — cruza VFC nocturna, predisposición y sueño para devolverte un veredicto accionable con su porqué.
- **PDF del entrenador → tu reloj** — sube el plan de maratón en PDF y lo convierte en etapas (calentamiento, series, enfriamiento) listas para el dispositivo.
- **Multi-usuario aislado** — cada corredor tiene su API key y sus credenciales Garmin guardadas por separado. Nadie ve la sesión del otro.
- **Web app incluida** — panel de administración (`/admin`), alta de corredores paso a paso (`/admin/users`), login y conexión Garmin guiada (`/connect`), landing pública (`/`).
- **Autohospedado** — desplegado en tu Dokploy, tu nube o tu casa. Tú decides dónde viven los datos.
- **Rutas sobre OpenStreetMap** — generación de rutas circulares desde casa con `osmnx`.
---
## 🚀 Cómo funciona
```
Garmin Connect → Garmin Coach MCP (tu servidor) → Claude / Cursor / VS Code / móvil
(API) (Docker / Dokploy) (MCP protocol)
```
Hay **3 pasos, una sola vez**:
1. **Recibe tu clave** — el administrador te crea una API key personal (`gcmcp_…`) desde `/admin/users`.
2. **Conecta tu Garmin** — metes tu correo y contraseña en el asistente seguro. Quedan guardados y aislados en tu carpeta de usuario.
3. **Entrena y pregunta** — abres Claude, Cursor o VS Code, lo conectas con tu clave y listo.
---
## 🖥️ Despliegue
### Opción A — Dokploy (recomendada)
Despliega el repositorio como un **aplicación Docker Compose** en Dokploy (dominio público, HTTPS con el proxy inverso incorporado).
```yaml
# docker-compose.yml (ya incluido en el repo)
services:
garmin-mcp:
build: .
image: garmincoachmcp-garminmcp
restart: unless-stopped
ports:
- "8000:8000"
environment:
- PORT=8000
- DATA_DIR=/data
- USERS_DB_DIR=/data/users
- PUBLIC_URL=${PUBLIC_URL:-} # ej: https://garmin.tudominio.com
- GARMIN_LANGUAGE=es
- GARMIN_TIMEZONE=Europe/Madrid
volumes:
- garmincoach_data:/data
healthcheck:
test: ["CMD", "python", "-c", "import urllib.request; urllib.request.urlopen('http://localhost:8000/health')"]
interval: 30s
timeout: 5s
retries: 3
start_period: 20s
volumes:
garmincoach_data: # persiste tokens Garmin y usuarios entre despliegues
```
### Opción B — Docker CLI
```bash
docker build -t garmin-coach-mcp .
docker run -d --name garmin-mcp \
-p 8000:8000 \
-e PUBLIC_URL=https://garmin.tudominio.com \
-v garmincoach_data:/data \
garmin-coach-mcp
```
### Opción C — Local (Python)
```bash
python -m venv .venv && source .venv/bin/activate
pip install -r requirements.txt
DATA_DIR=./data PUBLIC_URL=http://localhost:8000 python server.py
```
---
## ⚙️ Variables de entorno
| Variable | Default | Descripción |
|---|---|---|
| `PORT` | `8000` | Puerto del servidor. |
| `DATA_DIR` | `/data` | Raíz del volumen persistente (tokens, usuarios, config). |
| `USERS_DB_DIR` | `<DATA_DIR>/users` | Carpeta con la BBDD de usuarios y sus tokens. |
| `PUBLIC_URL` | *(vacío)* | URL pública del servicio (para enlaces de conexión). Ideal en Dokploy. |
| `ADMIN_API_KEY` | *(vacío)* | Si se define, bloquea `/admin/users` y exige esta clave. |
| `ADMIN_TOKEN` | *(vacío)* | Token para el panel de administración `/admin`. |
| `GARMIN_TOKENS_JSON` | *(vacío)* | Tokens Garmin en JSON (legacy single-user, base64). |
| `GARMIN_EMAIL` | *(vacío)* | Email asociado a los tokens legacy. |
| `GARMIN_LANGUAGE` | `es` | Idioma de las respuestas Garmin. |
| `GARMIN_TIMEZONE` | `Europe/Madrid` | Zona horaria de las métricas. |
| `CACHE_MINUTES` | `30` | Minutos de caché de datos Garmin. |
| `ACTIVITY_LIMIT` | `8` | Máx. actividades por consulta (1–20). |
| `RESET_GARMIN_TOKENS` | `0` | Pon a `1` para borrar tokens al arrancar. |
---
## 🔑 Rutas web
| Ruta | Descripción |
|---|---|
| `/` | Landing pública. |
| `/admin` | Panel de administración. |
| `/admin/users` | **Alta de corredores paso a paso** (wizard). |
| `/u/login?api_key=…` | Panel del corredor (por API key). |
| `/connect?api_key=…` | Asistente para conectar Claude / Cursor / móvil. |
| `/garmin-connect` | Conexión de la cuenta Garmin del corredor. |
| `/health` | Healthcheck (200 = vivo). |
---
## 🤖 Conectar un asistente
Desde `/connect?api_key=…` (o el panel del corredor `u/login`) obtienes la config exacta.
**Claude Desktop / Cursor (HTTP):**
```json
{
"mcpServers": {
"garmin-coach": {
"url": "https://tu-dominio/mcp",
"headers": { "X-User-API-Key": "TU_API_KEY" }
}
}
}
```
**Claude Code (CLI):**
```bash
claude mcp add --transport http garmin-coach https://tu-dominio/mcp \
--header "X-User-API-Key: TU_API_KEY"
```
**Móvil / Claude.ai:** usa un *Custom Connector* apuntando a `https://tu-dominio/mcp` con la cabecera `X-User-API-Key`.
> El correo y la contraseña de Garmin viven en tu servidor, nunca en el chat. Tu app solo guarda la API key personal.
---
## 🧩 Herramientas MCP destacadas
`get_daily_summary` · `get_hrv_data` · `detect_fatigue_risk` · `plan_this_week` · `parse_training_pdf` · `calculate_pace_zones` · `summarize_period` · `route_from_home` · `get_race_predictions` · `list_tools_spanish` … y **más de 110** hasta completar el cuaderno.
Pídele al asistente `list_tools_spanish` para ver el catálogo completo en directo.
---
## 🔒 Privacidad
- **Cada quien lo suyo** — tu sesión Garmin vive en tu carpeta de usuario; ni el vecino ni el admin la ven.
- **Solo la API key** — en tu app guardas solo tu clave personal; el correo de Garmin va al asistente, nunca al chat.
- **Autohospedado** — es tu servidor. Tú decides dónde viven los datos.
---
## 📁 Estructura
```
server.py # Servidor FastMCP + panel web (single-file)
index.html # Landing pública
Dockerfile # Imagen (instala GDAL/geos/proj para rutas)
docker-compose.yml # Despliegue en Dokploy con volumen /data
requirements.txt # Dependencias
```
---
## 🛠️ Desarrollo
```bash
git clone https://github.com/javipaur/garmin-coach-mcp.git
cd garmin-coach-mcp
python -m venv .venv && source .venv/bin/activate
pip install -r requirements.txt
DATA_DIR=./data python server.py
# → http://localhost:8000
```
---
Hecho con 🏃 para entrenar de forma más inteligente.
This server cannot be deployed
Maintenance
ActivityMaintained
ResponsivenessNo issues