Tous les articles
NginxProduction

Nginx en reverse proxy de production : le guide

Publié le 30 juillet 2024 · 10 min de lecture

Le reverse proxy, chef d'orchestre de votre stack

Sur la majorité des VPS que nous auditons, Nginx sert de porte d'entrée : il termine le TLS, distribue vers les applications, absorbe les pics. Une configuration de production tient en quatre blocs — les mêmes que nous recommandons au support.

TLS : la base non négociable

TLS 1.3, HSTS, et des paramètres modernes. Avec Let's Encrypt et certbot, le renouvellement est un non-sujet :

ssl_protocols TLSv1.3 TLSv1.2;
ssl_prefer_server_ciphers off;
add_header Strict-Transport-Security "max-age=63072000" always;

Gardez TLS 1.2 en repli tant que de vieux clients existent ; TLS 1.3 fait gagner un aller-retour à chaque nouvelle connexion.

WebSocket : les deux en-têtes qui manquent toujours

Une application temps réel qui fonctionne en local et échoue derrière le proxy ? Il manque l'upgrade :

location /ws {
    proxy_pass http://127.0.0.1:3000;
    proxy_http_version 1.1;
    proxy_set_header Upgrade $http_upgrade;
    proxy_set_header Connection "upgrade";
    proxy_read_timeout 3600s;
}

Le proxy_read_timeout évite que Nginx coupe les connexions inactives au bout de 60 secondes.

Rate limiting : votre premier pare-feu applicatif

limit_req_zone $binary_remote_addr zone=api:10m rate=10r/s;

location /api/ {
    limit_req zone=api burst=20 nodelay;
    proxy_pass http://127.0.0.1:3000;
}

Dix requêtes par seconde et par IP, avec une rafale tolérée de vingt. C'est trivial à mettre en place, et cela neutralise la majorité des scans et petits floods L7 — le reste est absorbé par notre anti-DDoS en amont.

Le microcache : une seconde qui change tout

Pour les pages quasi-statiques générées dynamiquement, un cache d'une seconde divise la charge par le nombre de visiteurs simultanés :

proxy_cache_path /var/cache/nginx levels=1:2 keys_zone=micro:10m inactive=60m;

location / {
    proxy_cache micro;
    proxy_cache_valid 200 1s;
    proxy_cache_use_stale updating;
    proxy_pass http://127.0.0.1:3000;
}

Sur un blog propulsé par un CMS, c'est la différence entre 40 req/s et 4 000 req/s sur le même VPS.

Les détails de production

  • proxy_set_header X-Real-IP $remote_addr; pour que l'application voie la vraie IP cliente
  • client_max_body_size 25m; pour les uploads, sans ouvrir à tout
  • Des proxy_connect_timeout courts (2 à 5 s) : un backend mort doit échouer vite
  • proxy_buffering on (défaut) : il protège vos backends des clients lents

Testez chaque modification avec nginx -t, rechargez avec systemctl reload nginx — zéro coupure, et aucune excuse pour tester en production à l'aveugle.