Quel est l'état actuel des choses lorsqu'il s'agit de faire ou non
Transfer-Encoding: gzip
ou un
Content-Encoding: gzip
lorsque je veux permettre à des clients avec par exemple une bande passante limitée de signaler leur volonté d'accepter une réponse compressée et que le serveur a le dernier mot sur la compression ou non .
C'est ce que font par exemple le mod_deflate d'Apache et IIS, si vous le laissez prendre en charge la compression. En fonction de la taille du contenu à compresser, il fera le plus Transfer-Encoding: chunked
.
Il comprendra également un Vary: Accept-Encoding
, qui fait déjà allusion au problème. Content-Encoding
semble faire partie de l'entité, donc changer les Content-Encoding
montants en un changement d'entité, c'est-à-dire un en- Accept-Encoding
tête différent signifie par exemple qu'un cache ne peut pas utiliser sa version mise en cache de l'entité par ailleurs identique.
Y a-t-il une réponse définitive à ce sujet que j'ai manquée (et qui n'est pas enterrée dans un message dans un long fil de discussion dans un groupe de discussion Apache)?
Mon impression actuelle est:
- Transfer-Encoding serait en fait la bonne façon de faire ce qui est principalement fait avec Content-Encoding par les implémentations existantes de serveur et de client
- Content-Encoding, en raison de ses implications sémantiques, pose quelques problèmes (que doit faire le serveur
ETag
lorsqu'il compresse une réponse de manière transparente?) - La raison en est chicken'n'egg: les navigateurs ne le prennent pas en charge parce que les serveurs ne le font pas parce que les navigateurs ne le font pas
Donc, je suppose que la bonne manière serait un Transfer-Encoding: gzip
(ou, si je découpais en plus le corps, il le deviendrait Transfer-Encoding: gzip, chunked
). Et aucune raison de toucher Vary
ou ETag
ou tout autre en-tête dans ce cas, car c'est une chose au niveau du transport.
Pour l'instant, je ne me soucie pas trop du «saut par saut» de Transfer-Encoding
, quelque chose dont les autres semblent se préoccuper avant tout, parce que les proxys peuvent décompresser et transmettre non compressés au client. Cependant, les proxys peuvent tout aussi bien le transmettre tel quel (compressé), si la demande d'origine a l'en- Accept-Encoding
tête approprié , ce qui dans le cas de tous les navigateurs que je connais est une donnée.
Btw, ce problème date d'au moins une décennie, voir par exemple https://bugzilla.mozilla.org/show_bug.cgi?id=68517 .
Toute clarification à ce sujet sera appréciée. À la fois en termes de ce qui est considéré comme conforme aux normes et de ce qui est considéré comme pratique. Par exemple, les bibliothèques clientes HTTP ne prenant en charge que le "Content-Encoding" transparent serait un argument contre l'aspect pratique.
la source
Transfer-Encoding:gzip
, bien que curl en ligne de commande le fasse. Pour être prudent, envoyez les deux, sauf si vous combinez chunked et gzip.Réponses:
Citant Roy T.Fielding , l'un des auteurs de la RFC 2616:
Source: https://issues.apache.org/bugzilla/show_bug.cgi?id=39727#c31
En d'autres termes: ne faites pas l' encodage de contenu à la volée , utilisez plutôt l'encodage de transfert!
Edit: Autrement dit, à moins que vous ne souhaitiez servir du contenu gzippé à des clients qui ne comprennent que le codage de contenu . Ce qui, malheureusement, semble être la plupart d'entre eux. Mais sachez que vous quittez les domaines de la spécification et que vous pourriez rencontrer des problèmes tels que celui mentionné par Fielding ainsi que d'autres, par exemple lorsque des proxys de mise en cache sont impliqués.
la source
TE: gzip
. Et puis votre serveur devrait suivre la route de transfert-encodage. Si le client le dit seulementAccept-Encoding: gzip
, vous devez le faire comme vous le souhaitezContent-Encoding
. Si le client ne spécifie ni l'un ni l'autre dans sa requête, le serveur ne doit pas du tout gzip.L' utilisation correcte , telle que définie dans la RFC 2616 et réellement implémentée dans la nature, consiste pour le client à envoyer un en-
Accept-Encoding
tête de demande (le client peut spécifier plusieurs codages). Le serveur peut alors, et alors seulement, coder la réponse selon les codages pris en charge par le client (si les données du fichier ne sont pas déjà stockées dans ce codage), indiquer dans l'en-Content-Encoding
tête de réponse quel codage est utilisé. Le client peut alors lire les données de la socket en fonction duTransfer-Encoding
(c'est-à-direchunked
), puis les décoder en fonction duContent-Encoding
(c'est-à-dire:)gzip
.Ainsi, dans votre cas, le client enverrait un en-
Accept-Encoding: gzip
tête de demande, puis le serveur pourrait décider de compresser (si ce n'est déjà fait) et d'envoyer un enContent-Encoding: gzip
-Transfer-Encoding: chunked
tête et éventuellement de réponse.Et oui, l'en-
Transfer-Encoding
tête peut être utilisé dans les requêtes, mais uniquement pour HTTP 1.1, ce qui nécessite que les implémentations client et serveur prennent en charge l'chunked
encodage dans les deux sens.ETag
identifie de manière unique les données de ressources sur le serveur, pas les données réellement transmises. Si une ressource URL donnée change saETag
valeur, cela signifie que les données côté serveur de cette ressource ont changé.la source
Content-Encoding
requiert différentETag
C'est d'ailleurs ce à quoi sert le bogue mod_deflate auquel je fais référence dans ma réponse. Je me demande pourquoi ce détail au niveau de l'application est dans la norme HTTP en premier lieu.Transfer-Encoding
Cependant, lorsque vous utilisez un paramètre de niveau de transport, il n'est pas nécessaire de modifier le fichierETag
. Sauf que personne n'a implémenté Transfer-Enc.Content-Encoding
vsTransfer-Encoding
. Oui, gzip doit être une propriété du transfert d'une ressource, s'il est effectué à la volée. En revanche, si la ressource est stockée compressée sur le serveur, elle doit plutôt être une propriété du contenu de la ressource, si elle est envoyée telle quelle . Mais ce qui devrait être et ce qui est réellement ne sont pas toujours la même chose.