Nous allons étudier les différentes méthodes afin de mettre en place une redirection HTTP vers HTTPS avec nginx.
Pourquoi mettre en place une redirection vers https?

Pourquoi ?

Depuis quelques mois la mise en place d’une version https d’un site web est devenu une action à ne pas négliger (pour ne pas dire obligatoire).
Ne pas mettre en place de version https de votre site peut avoir de nombreuses conséquences y compris si vous n’hébergez pas de données sensibles:
– Google donne un malus de référencement aux sites non disponible en https.
– Les principaux navigateurs web affichent maintenant des messages d’alertes lorsque vous vous connectez à un site en http.
– Les pages et informations consultées par les clients peuvent être modifiée pour y incorporer divers logiciels malveillants.
– Enfin toute donnée (type identifiants / mot de passe / adresse / code bancaires…) envoyée par le client peut être interceptée sans difficultés.
– Certaines autorités de certification délivrent gratuitement et facilement des certificats simple (let’s encrypt par exemple).

Il est donc peu couteux et essentiel aussi bien pour vous que pour vos clients de mettre en place une version https de votre site pour ensuite rediriger l’ensemble du trafic http vers cette version sécurisée.


Différentes méthode de redirection

Il existe plusieurs méthodes de redirection mais avant de les découvrir, il est nécessaire de connaitre quelques variables :
(http ou https) correspond au protocole utilisé par le client pour se connecter à votre serveur.
correspond au nom de domaine que le client cherche à joindre.
correspond à la ressources/page tel que demandée par le client (sans aucun retraitement).
correspond à la ressources/page demandée par le client “normalisé et interprété” par nginx.

Il existe les redirections 301 et 302, nous utiliserons ici la redirection de type 301.

redirection permanente, le navigateur du client mettra en cache cette redirection et la réalisera automatiquement sans contacter votre serveur (idéal pour une redirection http/https par exemple).
redirection temporaire, le navigateur ne mettra pas en cache la réponse et refera la demande à chaque fois. Cette redirection est idéal dans le cas d’une maintenance par exemple mais implique une petite surcharge de votre serveur puisque nous mise en cache.

Nous utiliserons ici des redirections 301.


Redirection 301

La redirection 301 se met en place de la manière suivante dans votre vhost :

# Redirection simple:
 return 301 https://$host$uri;
 
 # Redirection via réécriture:
 rewrite ^ https://$host$uri permanent;

Le module de réécriture d’url permet d’utiliser des règle de redirection plus complexe que la redirection simple en utilisant des regex (à insérer à la place du ^ )

Dans certaines configuration, il est nécessaire d’employer une configuration plus poussée:

#Exemple d'une configuration ou le vhost http et https sont dans le même bloc.
 server {
  listen 80;
  listen 443 ssl http2;
  
  server_name monsite.fr www.monsite.fr;
  
  root /var/www/monsite;
  index index.php index.ht
 
  ssl_certificate /etc/ssl/cert/monsite.fr.crt;
  ssl_certificate_key /etc/ssl/private/monsite.fr.key;
  
  access_log /var/log/nginx/monsite_access_log;
  error_log /var/log/nginx/monsite_error_log; 
 }

Il faudra donc insérer une condition avant la règle de redirection pour éviter une boucle de redirection:

# Force HTTPS connection if http
 if ($scheme != "https") {
  return 301 https://$host$uri;
 }

Dans le cas d’une configuration ou le serveur est situé derrière un loadbalanceur de type haproxy / AWS ELB ou derrière un serveur de cache type varnish il faudra utiliser les variables x_forwarded pour filtrer les requêtes http / https:

$http_x_forwarded_proto != 'https'

Test

La meilleure façon de tester le comportement d’un site web est d’utiliser curl en ligne de commande.
Si vous réaliser des tests via votre navigateur, faites attention au cache qui dans le cas de redirection 301 peuvent totalement fausser vos tests.

Voici le comportement que vous devriez obtenir:

curl -Ik http://monsite.fr
 HTTP/1.1 301 Moved Permanently
 Server: nginx
 Date: Fri, 21 Dec 2018 15:07:53 GMT
 Location: https://xxxx.jn-hebergement.com/status
 
 curl -Ik https://monsite.fr
 HTTP/1.1 200 OK
 Server: nginx
 Date: Fri, 21 Dec 2018 15:18:31 GMT