Doctolib MCP
README.md
# Doctolib MCP
Serveur [MCP](https://modelcontextprotocol.io) **non officiel** qui donne à Claude (ou à tout client MCP) un accès complet
à l'API publique de Doctolib : chercher des praticiens autour d'un lieu, lister **tous les créneaux libres** d'une
spécialité dans un rayon, lire les infos pratiques d'un cabinet, et **être alerté dès qu'un créneau se libère**.
> « Trouve-moi tous les rendez-vous de dermatologue dans les 15 km autour de Clermont-Ferrand d'ici un mois. »
> « Surveille le Dr X et préviens-moi sur mon téléphone dès qu'un créneau s'ouvre avant le 15 octobre. »
Aucun compte Doctolib n'est nécessaire : le serveur utilise uniquement les données publiques que le site affiche à
tout visiteur. La réservation, elle, se fait toujours sur Doctolib (lien direct fourni, lieu et motif pré-sélectionnés).
## Fonctionnalités
- **Recherche géographique** : spécialité + ville / code postal / adresse + rayon, triée par distance, avec secteur de
conventionnement, paiement, langues, motif, acceptation des nouveaux patients.
- **Tous les créneaux d'une zone en un appel** (`find_slots`) : chaque agenda est interrogé, les créneaux sont remis
dans l'ordre chronologique, avec la raison quand il n'y en a pas (« agenda fermé », « prochain créneau le … »).
- **Détail d'un praticien** : tous ses motifs (réservés aux patients suivis ? restrictions d'âge ? vidéo ?),
agendas fermés, téléphone du cabinet, horaires d'ouverture, carte Vitale, moyens de paiement.
- **Créneaux** sur la période voulue (au-delà des 15 jours par appel de Doctolib), avec **remplaçants** et créneaux sur demande.
- **Surveillance** d'un praticien ou de toute une zone, avec notifications **macOS**, **push téléphone**
([ntfy](https://ntfy.sh), gratuit) ou **webhook** (n8n, Make, Zapier…).
- **Référentiels** : 123 spécialités, autocomplétion Doctolib (spécialités, actes, praticiens), sitemaps publics.
21 outils au total : voir **[docs/TOOLS.md](docs/TOOLS.md)**. Les endpoints Doctolib sous-jacents sont documentés
dans **[docs/API.md](docs/API.md)**.
## Installation
Prérequis : Python ≥ 3.11 et [uv](https://docs.astral.sh/uv/).
```bash
git clone https://github.com/arvernesmotion/Doctolib-MCP.git
cd Doctolib-MCP
uv sync
```
### Claude Code
```bash
claude mcp add doctolib --scope user -- uv --directory /chemin/vers/Doctolib-MCP run doctolib-mcp
```
### Claude Desktop
Dans `claude_desktop_config.json` (voir [examples/claude_desktop_config.json](examples/claude_desktop_config.json)) :
```json
{
"mcpServers": {
"doctolib": {
"command": "uv",
"args": ["--directory", "/chemin/vers/Doctolib-MCP", "run", "doctolib-mcp"]
}
}
}
```
### Autres clients MCP
Le serveur parle MCP en **stdio** : commande `uv --directory <dossier> run doctolib-mcp`.
## Exemples de demandes
| Vous demandez | Outils utilisés |
|---|---|
| « Quels ophtalmos à moins de 10 km de Lyon prennent de nouveaux patients ? » | `search_practitioners` |
| « Tous les créneaux de kiné autour de Nantes cette semaine » | `find_slots` |
| « Ce médecin accepte-t-il la carte Vitale ? Quels sont ses horaires ? » | `practitioner_practical_info` |
| « Pourquoi je ne trouve aucun créneau chez ce dermato ? » | `practitioner_booking_info`, `get_availabilities` |
| « Préviens-moi dès qu'un pédiatre se libère à 15 km de Bordeaux » | `watch_area`, `configure_notifications` |
## Alertes de créneaux
1. **Choisir les canaux** (une fois) : demandez à Claude « configure les notifications avec un topic ntfy »
(`configure_notifications`), puis installez l'app **ntfy** (iOS / Android) et abonnez-vous au topic renvoyé.
Gardez-le secret : quiconque le connaît reçoit vos alertes. Un `webhook_url` permet aussi de relayer vers n8n, Slack…
2. **Créer une surveillance** : `watch_practitioner` (un praticien) ou `watch_area` (toute une zone).
3. **Planifier la vérification** : la commande `doctolib-mcp-watch` fait une passe et notifie les nouveaux créneaux.
Lancez-la toutes les 5 à 10 minutes :
- **macOS (launchd)** : adapter [examples/launchd.plist](examples/launchd.plist) puis
```bash
cp examples/launchd.plist ~/Library/LaunchAgents/fr.doctolib-mcp.watch.plist
launchctl bootstrap gui/$(id -u) ~/Library/LaunchAgents/fr.doctolib-mcp.watch.plist
```
⚠ Protection macOS : launchd refuse d'exécuter un script situé dans `~/Documents`, `~/Desktop` ou
`~/Downloads` (« Operation not permitted »). L'exemple appelle donc `.venv/bin/python -m doctolib_mcp.watch`.
Si la passe reste bloquée malgré tout, clonez le dépôt hors de ces dossiers (ex. `~/Services/Doctolib-MCP`).
- **Linux (systemd)** : [examples/doctolib-mcp-watch.service](examples/doctolib-mcp-watch.service) et
[examples/doctolib-mcp-watch.timer](examples/doctolib-mcp-watch.timer).
- **cron** : `*/10 * * * * cd /chemin/vers/Doctolib-MCP && uv run doctolib-mcp-watch >> ~/.doctolib-mcp/watch.log 2>&1`
Au premier passage, les créneaux déjà ouverts sont signalés ; ensuite, uniquement les nouveaux. Un créneau qui
disparaît puis réapparaît (annulation d'un autre patient) est signalé à nouveau : ce sont les meilleures occasions.
## Configuration
| Variable d'environnement | Défaut | Rôle |
|---|---|---|
| `DOCTOLIB_MCP_DATA` | `~/.doctolib-mcp` | Dossier des surveillances (`watches.json`) et de la configuration des alertes (`config.json`) |
| `DOCTOLIB_MCP_MIN_INTERVAL` | `0.35` | Délai minimal entre deux requêtes vers Doctolib (secondes) |
| `DOCTOLIB_MCP_USER_AGENT` | Chrome récent | User-Agent envoyé (obligatoire pour les créneaux) |
## Limites à connaître
- **Connexion résidentielle requise pour les créneaux.** Doctolib (Cloudflare) bloque `availabilities.json` depuis
les IP de datacenter (Vercel, AWS, la plupart des VPS…) : réponse 403. Faites tourner le serveur sur votre
ordinateur. La recherche et les infos pratiques passent, elles, depuis n'importe où.
- **Pas de réservation automatique.** Réserver exige votre compte Doctolib ; le serveur fournit le lien direct
(lieu + motif pré-sélectionnés). Le créneau lui-même ne peut pas être pré-sélectionné.
- **Seuls les agendas ouverts en ligne sont visibles.** Beaucoup de spécialistes n'ouvrent leur agenda que par vagues,
ou réservent certains motifs à leurs patients suivis ; c'est précisément là que la surveillance est utile.
- **Le motif principal** renvoyé par la recherche est choisi par Doctolib et peut être un motif réservé
(« Ancien patient du Dr X ») : `practitioner_booking_info` liste tous les motifs.
- **Tarifs chiffrés, accessibilité, RPPS** ne sont exposés que dans un endpoint réservé aux navigateurs : non couverts.
- **API non officielle** : Doctolib peut en changer le format à tout moment.
## Usage responsable
Ce projet n'est **ni affilié à Doctolib, ni approuvé par Doctolib**. Il est destiné à un **usage personnel**, pour
trouver un rendez-vous médical plus facilement. Le `robots.txt` et les conditions d'utilisation de Doctolib encadrent
l'accès automatisé à leurs services : restez à faible débit (réglage par défaut ≈ 3 requêtes/s, surveillances toutes
les 5–10 min), ne republiez pas et ne revendez pas les données, et n'utilisez pas cet outil pour accaparer des
créneaux au détriment d'autres patients. Vous êtes responsable de l'usage que vous en faites.
## Développement
```
src/doctolib_mcp/
├── client.py # HTTP : en-têtes navigateur, limitation de débit globale, reprises sur 429
├── api.py # un wrapper par endpoint Doctolib + normalisation
├── geo.py # géocodage (geo.api.gouv.fr, api-adresse.data.gouv.fr)
├── finder.py # moteur « tous les créneaux d'une zone »
├── store.py # surveillances, configuration, notifications
├── watch.py # passe de surveillance (commande doctolib-mcp-watch)
├── server.py # serveur MCP (21 outils + 1 ressource)
└── data/specialities.json
```
Test de bout en bout **contre le vrai site** (depuis une connexion résidentielle) :
```bash
uv run python tests/smoke_live.py
```
Il démarre le serveur en stdio, appelle chaque outil et affiche `OK` / `ERR` (les surveillances de test sont écrites
dans un dossier temporaire).
## Licence
[MIT](LICENSE)
This server cannot be deployed
Maintenance
ActivityMaintained
ResponsivenessNo issues