Strict-Transport-Security
Le header HSTS épingle HTTPS pour les prochaines visites, si bien que le navigateur ne retente jamais le HTTP en clair. Rôle et déploiement sûr.
Dernière mise à jour:
HTTP Strict Transport Security (HSTS) est un header de réponse qu'un site
envoie en HTTPS pour dire au navigateur de n'atteindre cet hôte qu'en HTTPS,
pendant une durée que vous choisissez. Une fois que le navigateur a vu le
header, il réécrit toute adresse http:// en clair de l'hôte en https://
avant même que la requête ne quitte la machine, même si l'utilisateur a tapé
l'adresse non sécurisée ou suivi un ancien lien.
Sans lui, taper un simple domaine dans la barre d'adresse commence par une requête HTTP en clair, et quiconque se trouve sur le chemin réseau (un point d'accès Wi-Fi public, un routeur compromis) peut lire ou réécrire ce saut non chiffré et maintenir la victime sur une version HTTP du site contrôlée par l'attaquant. HSTS supprime cette ouverture en faisant refuser au navigateur de parler HTTP en clair à votre hôte, tout simplement.
Voici le header tel que vous le déploieriez après un déploiement complet (voir comment le mettre en place avant de le copier) :
Strict-Transport-Security: max-age=63072000; includeSubDomains; preloadValeurs et ce que fait chacune
| Directive | Statut | Description |
|---|---|---|
max-age=<seconds> | ✅ Bon | Obligatoire. Durée pendant laquelle le navigateur impose HTTPS pour l'hôte. Le minuteur se réinitialise à chaque réponse, donc une valeur fixe n'expire pratiquement jamais pour les visiteurs qui reviennent. |
includeSubDomains | ✅ Bon | Étend la politique de l'hôte à tous ses sous-domaines, vers le bas uniquement. |
preload | ✅ Bon | Inscrit le domaine dans la liste de preload des navigateurs sur hstspreload.org. Non standard (absent du RFC 6797) et difficile à défaire ; ne soumettez que lorsque tout le domaine est prêt. |
max-age=0 | ❌ Risqué | L'interrupteur d'arrêt. Dit au navigateur d'oublier la politique, y compris includeSubDomains. Ne l'utilisez que pour revenir en arrière, et notez qu'il ne prend effet qu'à la prochaine réponse reçue en HTTPS valide. |
La politique s'attache à l'hôte exact qui a servi le header. Un header sur
www.example.com ne couvre jamais example.com, et il ne couvre les
sous-domaines que lorsque includeSubDomains est présent, et uniquement vers
le bas : une politique sur secure.example.com couvre
login.secure.example.com mais pas example.com ni les hôtes voisins. HSTS
identifie les hôtes par nom de domaine uniquement, donc il ne s'applique jamais
à un hôte adressé par IP. Les navigateurs ignorent entièrement le header quand
il arrive en HTTP en clair.
Contre quoi cela protège
- Le SSL stripping et les attaques de rétrogradation. Un attaquant actif sur le réseau peut intercepter une requête HTTP en clair et servir une version HTTP du site, tenant discrètement la victime hors de TLS. Avec HSTS, le navigateur passe l'URL en HTTPS avant que la requête ne parte, donc il n'y a aucune requête non sécurisée à intercepter.
- Le vol de cookie sur le premier saut non sécurisé. Sans le header, la
première requête vers un domaine tapé passe en HTTP en clair, et tout cookie
dépourvu de l'attribut
Secure(voir sécurité des cookies) voyage sur ce saut en clair, où un espion passif peut le copier. - Les erreurs de contenu mixte sur le même hôte. Les URL pointant vers un
hôte HSTS connu sont réécrites, donc une image ou une référence de script
http://égarée vers votre propre hôte est passée en HTTPS au lieu de se charger sans sécurité. - L'usurpation de certificat via un clic de contournement. Pour un hôte HSTS, le navigateur traite toute erreur de certificat comme fatale. Il n'y a pas de bouton « continuer quand même », donc un attaquant ne peut pas compter sur les utilisateurs pour cliquer au travers d'un avertissement lié à un certificat falsifié.
Risques sans le header
Chaque nouvelle visite commence sans sécurité. Quand un utilisateur tape votre
domaine ou suit un lien http://, le navigateur envoie la première requête en
HTTP en clair et attend votre redirection. Ce seul aller-retour non chiffré
suffit à un attaquant sur le chemin pour détourner la session : les cookies non
Secure voyagent en clair, et un attaquant actif peut répondre lui-même à la
requête et ne jamais laisser l'utilisateur atteindre HTTPS. Une redirection
côté serveur vers HTTPS ne comble pas cette faille, car la redirection n'a lieu
qu'après que la requête non sécurisée a déjà été envoyée et peut-être altérée.
Risques et pièges à l'usage
- La première visite n'est pas protégée. HSTS ne fonctionne qu'une fois que le navigateur a reçu le header au moins une fois en HTTPS valide. La toute première requête d'un nouveau navigateur, et la première requête après l'expiration de la politique, partent encore en HTTP en clair, sauf si le domaine figure sur la liste de preload.
- Le preload est quasi permanent. OWASP prévient de conséquences
permanentes si un site preloadé doit un jour repasser en HTTP. Le retrait de
la liste exige d'abord d'enlever la directive
preload, puis prend 6 à 12 semaines pour atteindre la plupart des utilisateurs de Chrome et plus longtemps pour les autres navigateurs, et les exigences de soumission s'appliquent tant que vous êtes listé. AvecincludeSubDomains, le preload force aussi chaque sous-domaine vers HTTPS, y compris les hôtes internes en HTTP seul que les navigateurs ne peuvent plus atteindre. Auditez tous les sous-domaines imbriqués avant de soumettre. - Des non-effets silencieux. La mauvaise configuration la plus courante est
d'envoyer le header sur des réponses HTTP en clair, que les navigateurs
doivent ignorer, donc rien ne se passe et rien ne vous avertit. Le header est
aussi ignoré sur les réponses présentant des erreurs de certificat. Et comme
la politique se lie à l'hôte exact, le servir sur
www.example.comalors que l'apexexample.comn'envoie rien laisse l'apex sans protection.
Comment le mettre en place
Augmentez max-age par étapes, comme le recommande
hstspreload.org, pour qu'une erreur bloque les
utilisateurs pendant des minutes, pas des années :
- Servez tout le site en HTTPS, y compris
wwwet chaque sous-domaine que vous comptez couvrir. - Configurez l'écouteur HTTP pour répondre à chaque requête par une redirection permanente (301) vers l'URL HTTPS, sans le header HSTS. Le RFC 6797 interdit de l'envoyer sur un transport non sécurisé, et les navigateurs l'ignorent de toute façon là.
- Ajoutez le header à toutes les réponses HTTPS avec d'abord une petite
valeur :
max-age=300; includeSubDomains(5 minutes). - Montez-la à
max-age=604800(1 semaine), puismax-age=2592000(1 mois), en laissant s'écouler lemax-agecomplet de chaque étape et en surveillant les casses avant l'étape suivante. - Assurez-vous que le domaine apex sert aussi le header, pas seulement
www; chaque hôte doit le recevoir directement. - Quand rien n'a cassé, passez à
max-age=63072000(2 ans) et, si vous voulez une protection dès la première visite, ajoutezpreloadet soumettez le domaine sur hstspreload.org. - Vérifiez le header déployé, et le reste de vos headers de réponse, avec le scanner de headers de sécurité.
Recommandation
Envoyez Strict-Transport-Security sur chaque réponse HTTPS, avec un max-age
de 2 ans, includeSubDomains et preload une fois le déploiement terminé :
Strict-Transport-Security: max-age=63072000; includeSubDomains; preloadC'est la valeur que recommande le
cheat sheet OWASP sur HTTP Strict Transport Security :
un max-age de 2 ans avec couverture des sous-domaines et preload. Traitez-la
comme l'état final, pas le point de départ. Atteignez-la via la montée
progressive ci-dessus, et n'ajoutez preload qu'une fois que chaque
sous-domaine tourne en HTTPS et que vous acceptez que la décision soit quasi
permanente.
Prise en charge par les navigateurs
Baseline largement disponible : Chrome, Firefox et Safari imposent tous le
header, donc la prise en charge est de fait universelle. La directive
preload ne fait pas partie du RFC 6797, mais la liste de preload qu'elle
alimente est consommée par tous les grands navigateurs.
FAQ
HSTS protège-t-il la première visite ?
Non. HSTS ne prend effet qu'une fois que le navigateur a reçu le header au moins une fois en HTTPS valide, si bien que la toute première requête d'un nouveau navigateur, et la première après l'expiration de la politique, partent encore en HTTP en clair. Le preload comble cet écart en embarquant la politique dans le navigateur.
Quel est un bon max-age pour HSTS ?
Deux ans (max-age=63072000) avec includeSubDomains et preload, la valeur que
recommande la cheat sheet OWASP. Ne commencez pas là. Montez depuis une petite
valeur comme max-age=300, en laissant s'écouler chaque étape et en surveillant
les casses, puis passez à l'état final de deux ans une fois que chaque sous-domaine
tourne en HTTPS.
Comment désactiver HSTS ?
Envoyez max-age=0 en HTTPS. Le navigateur cesse de traiter l'hôte comme un hôte
HSTS connu à la prochaine réponse qu'il reçoit en HTTPS valide, ce qui efface aussi
includeSubDomains. Si le domaine est preloadé, enlevez d'abord la directive
preload et utilisez le formulaire de retrait, qui met des semaines à se propager.
HSTS couvre-t-il les sous-domaines ?
Seulement lorsque includeSubDomains est présent, et uniquement vers le bas. La
politique s'attache à l'hôte exact qui a servi le header, donc un header sur
secure.example.com couvre login.secure.example.com mais pas example.com ni
les hôtes voisins. Sans includeSubDomains, il ne couvre que cet hôte, donc
l'apex doit envoyer son propre header.
Voir aussi
- Vue d'ensemble des headers de sécurité
- CSP upgrade-insecure-requests, qui passe en HTTPS les sous-ressources non sécurisées dans vos pages ; il complète HSTS plutôt qu'il ne le remplace
- Sécurité des cookies
pour l'attribut
Secureque HSTS ne remplace pas - Headers dépréciés, les headers de l'ère TLS (HPKP, Expect-CT) qui n'ont pas survécu
- Scanner de headers de sécurité pour vérifier vos headers déployés
Sources
Aperçu
Ce que sont les headers de sécurité HTTP, la liste complète avec leur statut, ce contre quoi chacun protège et où chacun est documenté.
Sécurité des cookies
Les attributs Set-Cookie qui protègent les sessions, Secure, HttpOnly, SameSite et les préfixes __Host- et __Secure-, expliqués simplement.