Contenu

Grav MCP Server : connecter Claude.ai à son site en 30 minutes

⚡ En bref

Connecter Claude.ai à son site Grav en 30 minutes : un plugin PHP expose 9 outils (lire, créer, modifier, supprimer des pages, gérer les plugins) via JSON-RPC 2.0, un proxy FastAPI gère l’authentification OAuth 2.1, et nginx fait le pont entre Internet et le homelab. Résultat : Claude peut lire et modifier le contenu du site directement depuis une conversation.

Le code est disponible sur GitHub :

🧠 Pourquoi

Le protocole MCP (Model Context Protocol) d’Anthropic permet à Claude.ai de se connecter à des sources de données externes via des outils standardisés. Jusqu’ici, aucun plugin MCP n’existait pour Grav CMS.

Ce stack maison permet de :

  • Lire et modifier les pages du site directement depuis Claude.ai sans ouvrir l’admin Grav
  • Automatiser la création de contenu bilingue (FR + EN) en une seule conversation
  • Déclencher des actions sur le site (vider le cache, activer/désactiver des plugins) par simple instruction
  • Chaîner les outils : créer une page → IndexNow + Google Indexing se déclenchent automatiquement

🔧 Ce qui a été fait

🏗️ Architecture globale

        Claude.ai
            │
            │ HTTPS (OAuth 2.1 + PKCE)
            ▼
    ┌───────────────┐
    │  Cloudflare   │  WAF + Cache
    └───────┬───────┘
            │
            ▼
    ┌───────────────┐
    │     nginx     │  SSL termination
    │  mcp.arleo.eu │  location /mcp → proxy
    └───────┬───────┘
            │
            ▼
    ┌───────────────┐
    │ FastAPI proxy │  Port 8083
    │  OAuth 2.1    │  Token validation
    │  mcp-proxy    │  SHA-256 hashing
    └───────┬───────┘
            │
            ▼
    ┌───────────────┐
    │  Plugin Grav  │  Port 8090 (interne)
    │  JSON-RPC 2.0 │  9 outils MCP
    │  PHP 8.3      │
    └───────────────┘

📦 Composants

Composant Technologie Rôle
grav-plugin-mcp-server PHP 8.3 Expose les outils MCP via JSON-RPC 2.0
mcp-oauth-proxy FastAPI + Python Gère OAuth 2.1, PKCE S256, tokens
nginx vhost nginx Reverse proxy SSL, location /mcp
systemd unit systemd Service hardeningé pour le proxy

🔌 Étape 1 — Installer le plugin Grav

# Cloner le plugin
git clone https://github.com/jmrGrav/grav-plugin-mcp-server.git \
  /var/www/grav/user/plugins/mcp-server

# Permissions
sudo chown -R www-data:www-data /var/www/grav/user/plugins/mcp-server

# Vider le cache Grav
cd /var/www/grav && sudo -u www-data php bin/grav clearcache

Le plugin expose un vhost interne sur 127.0.0.1:8090 — ajouter dans la config nginx de Grav :

# Vhost interne MCP — accessible uniquement depuis le proxy
server {
    listen 127.0.0.1:8090;
    server_name localhost;
    root /var/www/grav;
    index index.php;

    location / {
        try_files $uri $uri/ /index.php?$query_string;
    }

    location ~ \.php$ {
        fastcgi_pass unix:/run/php/php8.3-fpm.sock;
        fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
        include fastcgi_params;
    }

    # Bloquer l'accès direct au plugin PHP
    location ^~ /api/mcp {
        return 444;
    }
}

🔐 Étape 2 — Installer le proxy OAuth

# Cloner le proxy
git clone https://github.com/jmrGrav/mcp-oauth-proxy.git \
  /opt/mcp-oauth-proxy

# Créer l'utilisateur dédié
sudo useradd -r -s /bin/false mcp-proxy

# Créer l'environnement virtuel Python
cd /opt/mcp-oauth-proxy
python3 -m venv venv
venv/bin/pip install -r requirements.txt

# Configurer les secrets
sudo mkdir -p /etc/mcp-oauth-proxy
sudo cp secrets.env.example /etc/mcp-oauth-proxy/secrets.env
sudo nano /etc/mcp-oauth-proxy/secrets.env
# → Remplir MCP_CLIENT_ID, MCP_CLIENT_SECRET, MCP_TOKEN_SECRET

# Installer le service systemd
sudo cp systemd/mcp-oauth-proxy.service /etc/systemd/system/
sudo systemctl daemon-reload
sudo systemctl enable --now mcp-oauth-proxy

# Vérifier
sudo systemctl status mcp-oauth-proxy

🌐 Étape 3 — Configurer nginx

# Copier le vhost template
sudo cp nginx/mcp-vhost.conf /etc/nginx/sites-available/mcp
# Adapter votre-domaine.com et les chemins SSL
sudo nano /etc/nginx/sites-available/mcp

# Activer le vhost
sudo ln -s /etc/nginx/sites-available/mcp /etc/nginx/sites-enabled/
sudo nginx -t && sudo systemctl reload nginx

🤝 Étape 4 — Connecter Claude.ai

  1. Aller sur claude.aiSettingsConnectors
  2. Cliquer Add connector
  3. Entrer l’URL : https://mcp.votre-domaine.com/mcp
  4. Suivre le flux OAuth — autoriser l’accès
  5. Les 9 outils apparaissent dans la liste des connecteurs ✅

🛠️ Les 9 outils disponibles

Outil Description
list_pages Lister toutes les pages avec leurs routes et langues
get_page Lire le contenu Markdown d’une page
create_page Créer une nouvelle page
update_page Modifier le contenu ou le titre d’une page
delete_page Supprimer une page
clear_cache Vider le cache Grav
list_plugins Lister les plugins installés
list_themes Lister les thèmes installés
toggle_plugin Activer ou désactiver un plugin

🔒 Sécurité

Le proxy implémente plusieurs couches de protection :

  • OAuth 2.1 + PKCE S256 — flux d’authentification sécurisé conforme RFC 9728
  • SHA-256 token hashing — les tokens ne sont jamais stockés en clair
  • Atomic JSON writes — pas de corruption des fichiers d’état
  • Systemd hardeningNoNewPrivileges, ProtectSystem=strict, IPAddressDeny=any, MemoryDenyWriteExecute
  • nginx — blocage de l’accès direct au plugin PHP (location ^~ /api/mcp { return 444; })

🏁 Conclusion

Ce stack transforme Grav CMS en source de contexte active pour Claude.ai — lire, écrire, gérer le site par simple conversation. L’ensemble est reproductible sur n’importe quel serveur nginx avec Python 3.11+, et le code est entièrement disponible sur GitHub sous licence MIT.

Pour aller plus loin :

  • 💡 Ajouter des outils MCP supplémentaires : gestion des médias, des utilisateurs, des configurations système
  • 💡 Implémenter un système de permissions par outil pour restreindre les actions selon le token OAuth