Aussi disponible en : English · Español · Português · العربية
Vérificateur d'ETag
Comparez deux entity tags selon les fonctions de comparaison faible et forte, et voyez ce que chaque en-tête conditionnel en ferait.
Ce qu'est un ETag, et ce que signifie le W/
Un ETag est une chaîne opaque que le serveur attache à une version d'une ressource. Le client la conserve, la renvoie à la requête suivante, et le serveur peut répondre par un 304 au lieu du corps entier si rien n'a changé. La valeur obéit à une petite grammaire : un préfixe W/ facultatif, puis l'étiquette entre guillemets doubles obligatoires.
Les guillemets font partie de la valeur et ne sont pas décoratifs, et les caractères autorisés sont plus étroits qu'on ne le croit : l'ensemble est %x21 et de %x23 à %x7E, ce qui exclut le guillemet double et, moins évidemment, l'espace. La barre oblique inverse est admise, même si la spécification déconseille de l'employer, d'anciens destinataires pouvant tenter de la déséchapper.
Le préfixe W/ indique que l'étiquette est un validateur faible. L'explication habituelle est qu'une étiquette faible identifie une version sémantiquement équivalente plutôt qu'identique octet pour octet, ce qui est vrai et la fait passer pour une annotation mineure sur la précision. Elle ne l'est pas : elle change ce à quoi l'étiquette peut servir.
Comment s'en servir
- Mettez l'ETag du serveur dans le premier champ. Tel qu'il apparaît dans l'en-tête de réponse, guillemets et préfixe W/ compris. Ce qui est mal formé est expliqué plutôt qu'ignoré en silence.
- Mettez dans le second l'étiquette à laquelle on le compare. C'est en général ce qu'un client enverrait dans If-None-Match ou dans If-Match.
- Lisez les deux résultats, puis le tableau des en-têtes. Quand les deux fonctions divergent, la réponse dépend entièrement de l'en-tête qui pose la question, et le tableau ci-dessous détaille ce que chacun ferait.
Deux fonctions de comparaison, et celle dont personne ne parle
HTTP n'a pas une fonction de comparaison pour les entity tags. Il en a deux, et il en impose une différente selon l'endroit. La section 13.1.2 du RFC 9110 dit qu'un destinataire doit utiliser la comparaison faible pour If-None-Match. La 13.1.1 dit qu'un serveur d'origine doit utiliser la comparaison forte pour If-Match.
La comparaison faible ignore entièrement le préfixe W/ et compare les étiquettes opaques. La forte exige qu'elles soient égales et que les deux soient fortes. La conséquence est ce qu'il faut retenir : un ETag faible ne satisfait jamais la comparaison forte, pas même face à une copie identique de lui-même. La spécification l'imprime dans son propre tableau : W/"1" contre W/"1" correspond en comparaison faible et ne correspond pas en forte.
Un ETag faible se met donc parfaitement en cache et n'admet aucune écriture. Tout PUT ou PATCH conditionnel utilisant If-Match pour de l'accès concurrent optimiste échoue, toujours, quoi que le client envoie. Aucune erreur ne l'explique : la précondition ne passe simplement jamais. Si votre API renvoie 412 à chaque mise à jour et que l'ETag commence par W/, la voilà, la raison.
Ce n'est pas une configuration rare. Sur les 250 domaines les plus fréquentés, dont 173 ont répondu, seuls 20,2 % envoient un ETag — et parmi eux, 25,7 % sont faibles, dont wikipedia.org, github.com et apache.org. Pour une page mise en cache c'est un choix judicieux, car une étiquette faible survit à la compression et à d'autres transformations qui changent les octets sans changer le sens. Pour un point d'API que l'on met à jour, cela supprime une fonctionnalité dont personne ne sait qu'il l'a perdue.
If-Range est le troisième cas et fonctionne autrement. La restriction y pèse sur le client : la section 13.1.5 dit qu'un client ne doit pas produire d'en-tête If-Range contenant une étiquette faible, si bien que reprendre un téléchargement partiel exige un validateur fort par construction, et non par comparaison.
Limites assumées, et vérifications
Ceci compare deux étiquettes que vous collez. Aucune requête n'est émise, donc l'outil ne peut pas vous dire ce que votre propre serveur envoie : un navigateur ne peut pas lire des en-têtes de réponse arbitraires venant d'une autre origine, et tout outil qui prétend le contraire fait transiter la requête par un serveur. Les outils de développement de votre navigateur affichent l'en-tête en un clic, et c'est la bonne façon de l'obtenir.
Une chose que cette page se garde d'affirmer : que les serveurs émettraient couramment des ETags syntaxiquement invalides. C'était la seconde moitié de l'idée, et la mesure l'a tuée. Zéro des 35 ETags réels échantillonnés étaient mal formés. Cet en-tête est produit par des frameworks ; presque personne n'en écrit un à la main. Le validateur explique toujours une saisie mal formée, car qui en a tapé une mérite une réponse, mais ce n'est pas le fait intéressant et la page ne prétend pas le contraire.
La logique de comparaison est confrontée au tableau de quatre lignes de la spécification elle-même, réextrait du texte du RFC à chaque exécution des tests plutôt que recopié, si bien qu'une erreur de transcription ne peut pas survivre. Il y a 513 assertions et 14 contrôles négatifs. Deux de mes propres cas de test encodaient des suppositions plutôt que la grammaire : j'avais noté une étiquette contenant un espace comme valide et une contenant une barre oblique inverse comme invalide, et la grammaire dit l'inverse dans les deux cas.
Pourquoi est-ce gratuit ?
Il s'agit de comparer des chaînes. Cela s'exécute dans votre navigateur, il n'y a pas de serveur à payer et rien à quoi s'inscrire.
Rien de ce que vous saisissez n'est envoyé, conservé ni journalisé. Les ETags sont opaques par conception et encodent parfois plus de choses sur une ressource que leur auteur ne le pensait : il vaut donc la peine de préciser qu'ils restent dans l'onglet.