Table des matiĂšres de l'article :
Il existe de nombreux en-tĂȘtes HTTP diffĂ©rents qui peuvent ĂȘtre utilisĂ©s par votre site Web. Pour l'instant, nous allons nous concentrer sur un sous-ensemble spĂ©cifique de ceux-ci : les en-tĂȘtes de cache. Nous vous montrerons les dĂ©tails concernant les en-tĂȘtes de cache, afin que vous sachiez comment les utiliser Ă l'avenir !
Dans le contexte des sites Web et des applications, la mise en cache est définie comme le stockage de contenu dans une mémoire temporaire, telle que celle du navigateur ou de l'appareil de l'utilisateur ou sur un serveur intermédiaire, afin de réduire le temps nécessaire pour accéder à ce fichier .
Selon HTTP Archive, parmi les 300.000 XNUMX meilleurs sites, le navigateur de l'utilisateur peut mettre en cache prÚs de la moitié de tout le contenu téléchargé.
RĂ©duit le temps nĂ©cessaire Ă l'utilisateur pour visualiser des images ou des fichiers Javascript ou CSS. En effet, l'utilisateur accĂšde maintenant au fichier depuis son systĂšme au lieu d'ĂȘtre tĂ©lĂ©chargĂ© depuis le rĂ©seau. Dans le mĂȘme temps, la mise en cache rĂ©duit Ă©galement le nombre de requĂȘtes et de transferts de donnĂ©es depuis vos serveurs. Il s'agit sans aucun doute d'Ă©normes Ă©conomies pour les vues et les visites rĂ©pĂ©tĂ©es de la page.
Comment fonctionne la mise en cache ?
Supposons que nous ouvrions une page Web https://www.example.com et que le serveur renvoie le code HTML suivant :
...
<link type="text/css" href="https://www.example.com/app.css" rel="stylesheet">
...
<!-- Rest of the HTML -->
Lorsque le navigateur analyse ce code HTML, il identifie qu'une ressource CSS doit ĂȘtre chargĂ©e Ă partir de https://www.example.com/app.css .
Le navigateur envoie une requĂȘte au serveur pour ce fichier, le serveur renvoie le fichier et indique Ă©galement au navigateur de le mettre en cache pendant 30 jours. Plus loin dans ce guide, nous verrons comment le serveur envoie ces instructions au navigateur.
Maintenant, disons que vous ouvrez une autre page sur le mĂȘme site Web aprĂšs quelques heures. Le navigateur analyse Ă nouveau le code HTML et trouve Ă©galement le mĂȘme fichier CSS sur cette page : https://www.example.com/app.css . Ătant donnĂ© que le navigateur dispose de cette ressource particuliĂšre dans son cache local, il n'ira mĂȘme pas au serveur. La requĂȘte rĂ©seau n'est jamais faite, le fichier est accessible depuis le cache local et les styles sont appliquĂ©s trĂšs rapidement.
Comment est-il fait?
Il existe une gamme d'en-tĂȘtes de cache et de directives associĂ©es qui fournissent des instructions explicites Ă tout serveur d'utilisateur final, CDN et navigateur sur la façon de gĂ©rer le contenu mis en cache. La combinaison de plusieurs fonctionnalitĂ©s peut vous donner les rĂ©sultats souhaitĂ©s ou empĂȘcher le cache de fonctionner car elles ne sont pas utilisĂ©es correctement. Nous vous donnerons un aperçu rapide des en-tĂȘtes de cache HTTP les plus courants, de leurs directives et de la maniĂšre de les utiliser.
Cache-Control : directives
Plusieurs directives peuvent ĂȘtre utilisĂ©es pour contrĂŽler la fonctionnalitĂ© des en-tĂȘtes de cache. Vous n'ĂȘtes pas obligĂ© de les utiliser tous, alors choisissez ceux dont vous avez besoin et laissez les autres de cĂŽtĂ©. Voici les directives les plus importantes :
max-age
Dans la plupart des utilisations des en-tĂȘtes de contrĂŽle de cache, vous verrez cette directive en cours d'utilisation. Indique la durĂ©e maximale en secondes pendant laquelle les rĂ©ponses rĂ©cupĂ©rĂ©es peuvent ĂȘtre rĂ©utilisĂ©es Ă partir du moment oĂč une demande est faite. Par exemple: max-age=300
indique qu'une ressource peut ĂȘtre rĂ©utilisĂ©e pendant les 300 prochaines secondes. Cette ressource peut ĂȘtre mise en cache par le navigateur ou par n'importe quel cache en aval du serveur pendant cette pĂ©riode.
s-maxage
Il s-
le préfixe "" signifie partagé comme dans le cache partagé. Cette directive est explicitement pour CDN parmi d'autres caches intermédiaires. Cette directive prévaut sur max-age
directive et fait expirer le champ d'en-tĂȘte lorsqu'il est prĂ©sent. Il est important de se rappeler que cette directive n'affectera pas les navigateurs des visiteurs. Vous pouvez donc utiliser diffĂ©rentes valeurs pour mag-age
e s-maxage
spécifier des temps de cache différents pour les visiteurs et les CDN.
Cela peut ĂȘtre utile, par exemple si vous utilisez des systĂšmes de mise en cache tels que Vernis et souhaitez demander au serveur de cache de dĂ©finir un certain temps de cache pour certaines pages.
pas de cache
La no-cache
indique que les rĂ©ponses renvoyĂ©es ne peuvent pas ĂȘtre utilisĂ©es pour des requĂȘtes ultĂ©rieures vers la mĂȘme URL avant de vĂ©rifier si les rĂ©ponses du serveur ont Ă©tĂ© modifiĂ©es. Avec un ETag appropriĂ© (Ă©galement appelĂ© jeton de validation) prĂ©sent, par consĂ©quent, il se produit no-cache
un aller-retour pour tenter de valider les réponses mises en cache. Cependant, les caches peuvent supprimer les téléchargements si les ressources n'ont pas changé. Cela signifie que les navigateurs Web peuvent mettre en cache les actifs, mais doivent vérifier chaque demande si les actifs ont changé (le serveur renverra une réponse HTTP 304 si rien n'a changé).
sans magasin
Contrairement Ă no-cache
, la no-store
directive est plus simple. En effet, cela empĂȘche les navigateurs et tous les caches intermĂ©diaires de stocker toute version des rĂ©ponses renvoyĂ©es, telles que les rĂ©ponses contenant des informations privĂ©es/personnelles ou des informations bancaires. Chaque fois que les utilisateurs demandent cet actif, les demandes sont envoyĂ©es au serveur. Les ressources sont tĂ©lĂ©chargĂ©es Ă chaque fois.
public
Si une rĂ©ponse est marquĂ©e comme publique, elle peut ĂȘtre mise en cache mĂȘme dans les cas oĂč elle est associĂ©e Ă l'authentification HTTP ou si le code d'Ă©tat de la rĂ©ponse HTTP n'est normalement pas mis en cache. Ătant donnĂ© que les informations de mise en cache explicites, telles que via le max-age
directive, montre qu'une réponse est toujours en cache, l'utilisation de cette directive n'est généralement pas nécessaire.
Dans la plupart des cas, une réponse marquée comme publique n'est pas nécessaire, car les informations de mise en cache explicites (par ex. max-age
) montrent qu'une rĂ©ponse peut toujours ĂȘtre mise en cache.
Privé
Une rĂ©ponse marquĂ©e comme privĂ©e peut ĂȘtre mise en cache par le navigateur. Cependant, ces rĂ©ponses sont gĂ©nĂ©ralement destinĂ©es Ă des utilisateurs uniques, elles ne peuvent donc pas ĂȘtre mises en cache Ă partir de caches intermĂ©diaires (par exemple, les pages HTML contenant des informations utilisateur privĂ©es peuvent ĂȘtre mises en cache par le navigateur d'un utilisateur mais pas Ă partir d'un CDN).
expire
Il y a longtemps, cet en-tĂȘte Ă©tait utilisĂ© pour exploiter les mĂ©canismes de mise en cache. Cet en-tĂȘte contient simplement un horodatage. Il est toujours utile pour les agents utilisateurs plus anciens, mais il est important de noter que le Cache-Control max-age
avoir s-maxage
encore la priorité sur la plupart des systÚmes modernes.
derniĂšre modification
Cet en-tĂȘte est l'un des validateurs les plus courants pour le cache. Indique quand une ressource demandĂ©e a Ă©tĂ© modifiĂ©e pour la derniĂšre fois. Bien qu'il soit l'un des validateurs les plus courants, ses origines remontent Ă l'Ăšre HTTP / 1.0, ce qui en fait un validateur hĂ©ritĂ©.
étiqueter
Une nouvelle mĂ©thode de validation est l'utilisation d'ETag. C'est devenu la norme depuis HTTP/1.1. Ceci est validĂ© via un champ d'en-tĂȘte ETag. Il est gĂ©nĂ©ralement basĂ© sur un hachage du contenu demandĂ©, mais ce n'est pas obligatoire. Cependant, le client qui en fait la demande ne doit pas savoir comment il est gĂ©nĂ©rĂ©. Si un client a un objet dans son cache qui a expirĂ©, il peut utiliser l'ETag pour envoyer une requĂȘte HTTP au serveur. Le serveur vĂ©rifiera ensuite ce jeton par rapport aux ressources mises en cache. Si le bien n'a pas Ă©tĂ© modifiĂ©, le serveur peut retourner une rĂ©ponse 304 inchangĂ©e au client. Cela rĂ©gĂ©nĂ©rera la durĂ©e de vie de la ressource mise en cache, au lieu de recharger la ressource.
Etag peut ĂȘtre un en-tĂȘte de validation de remplacement ou complĂ©mentaire Ă last-modified. Il peut ĂȘtre particuliĂšrement utile de l'implĂ©menter lorsqu'il s'agit d'en-tĂȘtes de derniĂšre modification incorrects ou lorsqu'il est nĂ©cessaire de les dĂ©sactiver en supprimant l'en-tĂȘte.
Voyons quelques cas pratiques
Tout type de mise en cache fonctionnerait normalement par mise Ă jour et validation. Expliquons ce que cela signifie. Les nouvelles demandes vous donneront gĂ©nĂ©ralement une nouvelle copie du contenu servi instantanĂ©ment Ă partir du cache. Cependant, une reprĂ©sentation validĂ©e renverra rarement la copie entiĂšre si elle n'a pas changĂ© depuis la derniĂšre fois que vous l'avez demandĂ©e. Dans les cas oĂč il n'y a pas de validateur prĂ©sent (par exemple, un ETag ou un en-tĂȘte Last-Modified) combinĂ© Ă un manque d'informations de fraĂźcheur, il sera gĂ©nĂ©ralement considĂ©rĂ© comme non-cachable.
L'obtention d'une mise en cache appropriée offre d'énormes avantages en termes de performances, économise de la bande passante et réduit les coûts de serveur, mais de nombreux sites utilisent la moitié de la mise en cache, créant des conditions de concurrence entraßnant une perte de synchronisation des ressources interdépendantes.
La grande majorité des meilleures pratiques de mise en cache relÚvent de l'un des deux modÚles suivants :
Schéma 1 : contenu immuable + max-age
Cache-Control: max-age = 31536000
- Le contenu de cette URL ne change jamais, donc...
- Le navigateur/CDN peut mettre en cache cette ressource pendant un an sans problĂšme
- Le contenu en cache de moins de
max-age
les secondes peuvent ĂȘtre utilisĂ©es sans consulter le serveur
Dans ce modĂšle, vous ne modifiez jamais le contenu d'une certaine URL, vous modifiez l'URL :
<script src="/script-f93bca2c.js"></script>
<link rel="stylesheet" href="/styles-a837cb1e.css" />
<img src="/cats-0e9a2ef4.jpg" alt="âŠ" />
Chaque URL contient quelque chose qui change avec son contenu. Il peut s'agir d'un numéro de version, d'une date de modification ou d'un hachage du contenu, ce que je fais sur ce blog.
Cependant, ce modĂšle ne fonctionne pas pour des choses comme les articles et les billets de blog. Leurs URL ne peuvent pas ĂȘtre versionnĂ©es et leur contenu doit pouvoir changer. SĂ©rieusement, Ă©tant donnĂ© les fautes de grammaire et d'orthographe de base que je fais, je dois pouvoir mettre Ă jour le contenu rapidement et frĂ©quemment.
Schéma 2 : contenu éditable, toujours revalidé par le serveur
ContrĂŽle de cache: no-cache
- Le contenu de cette URL peut changer, alors ...
- Toute version mise en cache localement n'est pas approuvée sans l'autorisation du serveur
Observation: no-cache
cela ne signifie pas "ne pas mettre en cache", cela signifie qu'il doit vérifier (ou "revalider" comme il l'appelle) avec le serveur avant d'utiliser la ressource mise en cache. no-store
indique au navigateur de ne pas le mettre en cache du tout. Aussi must-revalidate
cela ne signifie pas "doit revalider", cela signifie que la ressource locale peut ĂȘtre utilisĂ©e si elle est plus jeune que celle fournie max-age
, sinon il doit ĂȘtre revalidĂ©. Oui je sais.
Dans ce modĂšle, vous pouvez ajouter un en-tĂȘte ETag
(un ID de version de votre choix) ou un Last-Modified
donnée en réponse. La prochaine fois que le client récupÚre la ressource, il renvoie la valeur du contenu qu'il possÚde déjà via If-None-Match
e If-Modified-Since
respectivement, permettant au serveur de dire "N'utilisez que ce que vous avez déjà , il est à jour" ou lorsque vous épelez "HTTP 304".
Si vous envoyez ETag
/ Last-Modified
ce n'est pas possible, le serveur envoie toujours l'intégralité du contenu.
Ce modÚle implique toujours une récupération du réseau, il n'est donc pas aussi bon que le modÚle 1 qui peut complÚtement contourner le réseau.
Il n'est pas rare d'ĂȘtre rebutĂ© par l'infrastructure nĂ©cessaire pour le modĂšle 1, mais Ă©galement d'ĂȘtre rebutĂ© par la demande de rĂ©seau requise par le modĂšle 2 et de choisir Ă la place quelque chose entre les deux : un max-age
contenu petit et variable. C'est un beau compromis.
max-age sur le changement de contenu est souvent le mauvais choix
⊠Et malheureusement ce n'est pas rare, par exemple cela arrive sur les pages de Github.
Imaginer:
/article/
/styles.css
/script.js
... le tout servi avec :
Cache-Control : doit ĂȘtre revalidĂ©, max-age = 600
- Le contenu des URL change
- Si votre navigateur a une version en cache de moins de 10 minutes, utilisez-la sans consulter le serveur
- Si ce n'est pas le cas, effectuez une récupération du réseau à l'aide de
If-Modified-Since
oIf-None-Match
si disponible
Ce modÚle peut sembler fonctionner pendant les tests, mais il décompose les choses dans le monde réel et est vraiment difficile à retrouver. Dans l'exemple ci-dessus, le serveur avait en fait mis à jour le HTML, le CSS et le JS, mais la page s'est retrouvée avec l'ancien HTML et le JS du cache et le CSS mis à jour du serveur. L'incompatibilité de version a cassé les choses.
Souvent, lorsque nous apportons des modifications importantes au HTML, nous sommes susceptibles de modifier Ă©galement le CSS pour reflĂ©ter la nouvelle structure et de mettre Ă jour le JS pour s'adapter aux changements de style et de contenu. Ces ressources sont interdĂ©pendantes, mais les en-tĂȘtes de mise en cache ne peuvent pas l'exprimer. Les utilisateurs peuvent se retrouver avec la nouvelle version d'une/deux des ressources, mais l'ancienne version de l'autre(s).
max-age
il est relatif au temps de rĂ©ponse, donc si toutes les ressources ci-dessus sont nĂ©cessaires dans le cadre de la mĂȘme navigation, elles expireront Ă peu prĂšs au mĂȘme moment, mais il y a toujours une petite chance d'une course lĂ -bas. Si vous avez des pages qui n'incluent pas JS ou qui incluent des CSS diffĂ©rents, les dates d'expiration peuvent ne pas ĂȘtre synchronisĂ©es. Et pire, le navigateur supprime continuellement des Ă©lĂ©ments du cache et ne sait pas que HTML, CSS et JS sont interdĂ©pendants, il publiera donc volontiers l'un mais pas l'autre. Multipliez tout cela ensemble et il n'est pas improbable que vous vous retrouviez avec des versions incompatibles de ces ressources.
Pour l'utilisateur, cela peut entraßner des problÚmes de mise en page et / ou de fonctionnalité. Des petits défauts au contenu totalement inutilisable.