7. Routage des Messages HTTP (Routing HTTP Messages)
Le routage des messages de requête HTTP est déterminé par chaque client en fonction de la ressource cible, de la configuration du proxy du client et de l'établissement ou de la réutilisation d'une connexion entrante. Le routage de réponse correspondant suit la même chaîne de connexion vers le client.
7.1. Détermination de la Ressource Cible (Determining the Target Resource)
Bien que HTTP soit utilisé dans une grande variété d'applications, la plupart des clients s'appuient sur le même mécanisme d'identification des ressources et les mêmes techniques de configuration que les navigateurs Web à usage général. Même lorsque les options de communication sont codées en dur dans la configuration d'un client, nous pouvons penser à leur effet combiné comme une référence URI (Section 4.1).
Une référence URI est résolue sous sa forme absolue afin d'obtenir l'「URI cible」(target URI). L'URI cible exclut le composant de fragment de la référence, le cas échéant, puisque les identifiants de fragment sont réservés au traitement côté client ([URI], Section 3.5).
Pour effectuer une action sur une「ressource cible」(target resource), le client envoie un message de requête contenant suffisamment de composants de son URI cible analysée pour permettre aux destinataires d'identifier cette même ressource. Pour des raisons historiques, les composants de l'URI cible analysée, collectivement appelés「cible de requête」(request target), sont envoyés dans les données de contrôle du message et le champ d'en-tête Host (Section 7.2).
Il existe deux cas inhabituels pour lesquels les composants de la cible de requête sont sous une forme spécifique à la méthode :
-
Pour CONNECT (Section 9.3.6), la cible de requête est le nom d'hôte et le numéro de port de la destination du tunnel, séparés par deux points.
-
Pour OPTIONS (Section 9.3.7), la cible de requête peut être un astérisque unique ("*").
Voir les définitions de méthode respectives pour plus de détails. Ces formes NE DOIVENT PAS (MUST NOT) être utilisées avec d'autres méthodes.
À la réception de la requête d'un client, un serveur reconstruit l'URI cible à partir des composants reçus conformément à leur configuration locale et au contexte de connexion entrante. Cette reconstruction est spécifique à chaque version majeure du protocole. Par exemple, la Section 3.3 de [HTTP/1.1] définit comment un serveur détermine l'URI cible d'une requête HTTP/1.1.
Note : Les spécifications précédentes définissaient l'URI cible recomposée comme un concept distinct, l'「URI de requête effective」(effective request URI).
7.2. Host et :authority
Le champ d'en-tête「Host」dans une requête fournit les informations d'hôte et de port de l'URI cible, permettant au serveur d'origine de distinguer les ressources tout en traitant les requêtes pour plusieurs noms d'hôtes.
Dans HTTP/2 [HTTP/2] et HTTP/3 [HTTP/3], le champ d'en-tête Host est, dans certains cas, supplanté par le champ pseudo-en-tête「:authority」des données de contrôle d'une requête.
Host = uri-host [ ":" port ] ; Section 4
Les informations d'autorité de l'URI cible sont critiques pour le traitement d'une requête. Un agent utilisateur DOIT (MUST) générer un champ d'en-tête Host dans une requête à moins qu'il n'envoie ces informations en tant que champ pseudo-en-tête「:authority」. Un agent utilisateur qui envoie Host DEVRAIT (SHOULD) l'envoyer comme premier champ dans la section d'en-tête d'une requête.
Par exemple, une requête GET vers le serveur d'origine pour http://www.example.org/pub/WWW/ commencerait par :
GET /pub/WWW/ HTTP/1.1
Host: www.example.org
Puisque les informations d'hôte et de port agissent comme un mécanisme de routage au niveau de l'application, elles sont une cible fréquente pour les logiciels malveillants cherchant à empoisonner un cache partagé ou à rediriger une requête vers un serveur non intentionnel. Un proxy d'interception est particulièrement vulnérable s'il s'appuie sur les informations d'hôte et de port pour rediriger les requêtes vers les serveurs internes, ou pour une utilisation comme clé de cache dans un cache partagé, sans d'abord vérifier que la connexion interceptée cible une adresse IP valide pour cet hôte.
7.3. Routage des Requêtes Entrantes (Routing Inbound Requests)
Une fois que l'URI cible et son origine sont déterminés, un client décide si une requête réseau est nécessaire pour accomplir la sémantique souhaitée et, si oui, où cette requête doit être dirigée.
7.3.1. Vers un Cache (To a Cache)
Si le client a un cache [CACHING] et que la requête peut être satisfaite par celui-ci, alors la requête est généralement dirigée là d'abord.
7.3.2. Vers un Proxy (To a Proxy)
Si la requête n'est pas satisfaite par un cache, alors un client typique vérifiera sa configuration pour déterminer si un proxy doit être utilisé pour satisfaire la requête. La configuration du proxy est dépendante de l'implémentation, mais est souvent basée sur la correspondance de préfixe URI, la correspondance d'autorité sélective, ou les deux, et le proxy lui-même est généralement identifié par un URI「http」ou「https」.
Si un proxy「http」ou「https」est applicable, le client se connecte en entrée en établissant (ou en réutilisant) une connexion à ce proxy, puis en lui envoyant un message de requête HTTP contenant une cible de requête qui correspond à l'URI cible du client.
7.3.3. Vers l'Origine (To the Origin)
Si aucun proxy n'est applicable, un client typique invoquera une routine de gestionnaire (spécifique au schéma de l'URI cible) pour obtenir l'accès à la ressource identifiée. La façon dont cela est accompli dépend du schéma de l'URI cible et est définie par sa spécification associée.
La Section 4.3.2 définit comment obtenir l'accès à une ressource「http」en établissant (ou en réutilisant) une connexion entrante vers le serveur d'origine identifié, puis en lui envoyant un message de requête HTTP contenant une cible de requête qui correspond à l'URI cible du client.
La Section 4.3.3 définit comment obtenir l'accès à une ressource「https」en établissant (ou en réutilisant) une connexion entrante sécurisée vers un serveur d'origine qui fait autorité pour l'origine identifiée, puis en lui envoyant un message de requête HTTP contenant une cible de requête qui correspond à l'URI cible du client.
7.4. Rejet des Requêtes Mal Dirigées (Rejecting Misdirected Requests)
Une fois qu'une requête est reçue par un serveur et analysée suffisamment pour déterminer son URI cible, le serveur décide s'il doit traiter la requête lui-même, transférer la requête à un autre serveur, rediriger le client vers une ressource différente, répondre avec une erreur ou abandonner la connexion. Cette décision peut être influencée par tout ce qui concerne la requête ou le contexte de connexion, mais est spécifiquement dirigée vers la question de savoir si le serveur a été configuré pour traiter les requêtes pour cet URI cible et si le contexte de connexion est approprié pour cette requête.
Par exemple, une requête pourrait avoir été mal dirigée, délibérément ou accidentellement, de sorte que les informations dans un champ d'en-tête Host reçu diffèrent de l'hôte ou du port de la connexion. Si la connexion provient d'une passerelle de confiance, une telle incohérence peut être attendue ; sinon, elle pourrait indiquer une tentative de contourner les filtres de sécurité, de tromper le serveur pour qu'il livre du contenu non public ou d'empoisonner un cache. Voir la Section 17 pour les considérations de sécurité concernant le routage des messages.
À moins que la connexion ne provienne d'une passerelle de confiance, un serveur d'origine DOIT (MUST) rejeter une requête si des exigences spécifiques au schéma pour l'URI cible ne sont pas satisfaites. En particulier, une requête pour une ressource「https」DOIT (MUST) être rejetée à moins qu'elle n'ait été reçue sur une connexion qui a été sécurisée via un certificat valide pour l'origine de cet URI cible, comme défini par la Section 4.2.2.
Le code d'état 421 (Misdirected Request) dans une réponse indique que le serveur d'origine a rejeté la requête parce qu'elle semble avoir été mal dirigée (Section 15.5.20).
7.5. Corrélation de Réponse (Response Correlation)
Une connexion pourrait être utilisée pour plusieurs échanges requête/réponse. Le mécanisme utilisé pour corréler entre les messages de requête et de réponse dépend de la version ; certaines versions de HTTP utilisent l'ordonnancement implicite des messages, tandis que d'autres utilisent un identifiant explicite.
Toutes les réponses, quel que soit le code d'état (y compris les réponses intermédiaires) peuvent être envoyées à tout moment après la réception d'une requête, même si la requête n'est pas encore complète. Une réponse peut se terminer avant que sa requête correspondante ne soit complète (Section 6.1). De même, les clients ne sont pas censés attendre une durée spécifique pour une réponse. Les clients (y compris les intermédiaires) peuvent abandonner une requête si la réponse n'est pas reçue dans un délai raisonnable.
Un client qui reçoit une réponse alors qu'il envoie encore la requête associée DEVRAIT (SHOULD) continuer à envoyer cette requête à moins qu'il ne reçoive une indication explicite du contraire (voir, par exemple, la Section 9.5 de [HTTP/1.1] et la Section 6.4 de [HTTP/2]).
7.6. Transfert de Messages (Message Forwarding)
Comme décrit dans la Section 3.7, les intermédiaires peuvent jouer divers rôles dans le traitement des requêtes et réponses HTTP. Certains intermédiaires sont utilisés pour améliorer les performances ou la disponibilité. D'autres sont utilisés pour le contrôle d'accès ou pour filtrer le contenu. Puisqu'un flux HTTP a des caractéristiques similaires à une architecture de type pipe-and-filter, il n'y a pas de limites inhérentes à l'étendue qu'un intermédiaire peut améliorer (ou interférer) avec l'une ou l'autre direction du flux.
Les intermédiaires sont censés transférer les messages même lorsque les éléments de protocole ne sont pas reconnus (par exemple, nouvelles méthodes, codes d'état ou noms de champs) puisque cela préserve l'extensibilité pour les destinataires en aval.
Un intermédiaire n'agissant pas comme un tunnel DOIT (MUST) implémenter le champ d'en-tête Connection, comme spécifié dans la Section 7.6.1, et exclure les champs de la transmission qui sont uniquement destinés à la connexion entrante.
Un intermédiaire NE DOIT PAS (MUST NOT) transférer un message à lui-même à moins qu'il ne soit protégé contre une boucle de requête infinie. En général, un intermédiaire devrait reconnaître ses propres noms de serveur, y compris tous les alias, variations locales ou adresses IP littérales, et répondre directement à de telles requêtes.
Un message HTTP peut être analysé comme un flux pour un traitement incrémental ou un transfert en aval. Cependant, les expéditeurs et les destinataires ne peuvent pas compter sur la livraison incrémentale de messages partiels, car certaines implémentations mettront en mémoire tampon ou retarderont le transfert de messages pour des raisons d'efficacité réseau, de vérifications de sécurité ou de transformations de contenu.
7.6.1. Connection
Le champ d'en-tête「Connection」permet à l'expéditeur de lister les options de contrôle souhaitées pour la connexion actuelle.
Connection = #connection-option
connection-option = token
Les options de connexion ne sont pas sensibles à la casse.
Lorsqu'un champ autre que Connection est utilisé pour fournir des informations de contrôle pour ou sur la connexion actuelle, l'expéditeur DOIT (MUST) lister le nom de champ correspondant dans le champ d'en-tête Connection. Notez que certaines versions de HTTP interdisent l'utilisation de champs pour de telles informations, et par conséquent n'autorisent pas le champ Connection.
Les intermédiaires DOIVENT (MUST) analyser un champ d'en-tête Connection reçu avant qu'un message ne soit transféré et, pour chaque connection-option dans ce champ, supprimer tout champ d'en-tête ou de trailer du message portant le même nom que la connection-option, puis supprimer le champ d'en-tête Connection lui-même (ou le remplacer par les propres options de contrôle de l'intermédiaire pour le message transféré).
Ainsi, le champ d'en-tête Connection fournit un moyen déclaratif de distinguer les champs qui sont uniquement destinés au destinataire immédiat (「hop-by-hop」) de ceux qui sont destinés à tous les destinataires de la chaîne (「end-to-end」), permettant au message d'être auto-descriptif et permettant aux futures extensions spécifiques à la connexion d'être déployées sans craindre qu'elles ne soient transférées aveuglément par des intermédiaires plus anciens.
De plus, les intermédiaires DEVRAIENT (SHOULD) supprimer ou remplacer les champs qui sont connus pour nécessiter une suppression avant le transfert, qu'ils apparaissent ou non comme une connection-option, après avoir appliqué la sémantique de ces champs. Cela inclut mais n'est pas limité à :
- Proxy-Connection (Annexe C.2.2 de [HTTP/1.1])
- Keep-Alive (Section 19.7.1 de [RFC2068])
- TE (Section 10.1.4)
- Transfer-Encoding (Section 6.1 de [HTTP/1.1])
- Upgrade (Section 7.8)
Un expéditeur NE DOIT PAS (MUST NOT) envoyer une option de connexion correspondant à un champ qui est destiné à tous les destinataires du contenu. Par exemple, Cache-Control n'est jamais approprié comme option de connexion (Section 5.2 de [CACHING]).
Les options de connexion ne correspondent pas toujours à un champ présent dans le message, car un champ spécifique à la connexion pourrait ne pas être nécessaire s'il n'y a pas de paramètres associés à une option de connexion. En revanche, un champ spécifique à la connexion reçu sans option de connexion correspondante indique généralement que le champ a été incorrectement transféré par un intermédiaire et devrait être ignoré par le destinataire.
Lors de la définition d'une nouvelle option de connexion qui ne correspond pas à un champ, les auteurs de spécification devraient quand même réserver le nom de champ correspondant afin d'éviter des collisions ultérieures. Ces noms de champs réservés sont enregistrés dans le「Registre des Noms de Champs du Protocole de Transfert Hypertexte (HTTP)」(Section 16.3.1).
7.6.2. Max-Forwards
Le champ d'en-tête「Max-Forwards」fournit un mécanisme avec les méthodes de requête TRACE (Section 9.3.8) et OPTIONS (Section 9.3.7) pour limiter le nombre de fois que la requête est transférée par des proxies. Cela peut être utile lorsque le client tente de tracer une requête qui semble échouer ou boucler à mi-parcours.
Max-Forwards = 1*DIGIT
La valeur Max-Forwards est un entier décimal indiquant le nombre restant de fois que ce message de requête peut être transféré.
Chaque intermédiaire qui reçoit une requête TRACE ou OPTIONS contenant un champ d'en-tête Max-Forwards DOIT (MUST) vérifier et mettre à jour sa valeur avant de transférer la requête. Si la valeur reçue est zéro (0), l'intermédiaire NE DOIT PAS (MUST NOT) transférer la requête ; au lieu de cela, l'intermédiaire DOIT (MUST) répondre en tant que destinataire final. Si la valeur Max-Forwards reçue est supérieure à zéro, l'intermédiaire DOIT (MUST) générer un champ Max-Forwards mis à jour dans le message transféré avec une valeur de champ qui est la plus petite de a) la valeur reçue décrémentée de un (1) ou b) la valeur maximale supportée par le destinataire pour Max-Forwards.
Un destinataire PEUT (MAY) ignorer un champ d'en-tête Max-Forwards reçu avec d'autres méthodes de requête.
7.6.3. Via
Le champ d'en-tête「Via」indique la présence de protocoles et de destinataires intermédiaires entre l'agent utilisateur et le serveur (sur les requêtes) ou entre le serveur d'origine et le client (sur les réponses), similaire au champ d'en-tête「Received」dans le courrier électronique (Section 3.6.7 de [RFC5322]). Via peut être utilisé pour suivre les transferts de messages, éviter les boucles de requêtes et identifier les capacités de protocole des expéditeurs le long de la chaîne requête/réponse.
Via = #( received-protocol RWS received-by [ RWS comment ] )
received-protocol = [ protocol-name "/" ] protocol-version
; voir Section 7.8
received-by = pseudonym [ ":" port ]
pseudonym = token
Chaque membre de la valeur du champ Via représente un proxy ou une passerelle qui a transféré le message. Chaque intermédiaire ajoute ses propres informations sur la façon dont le message a été reçu, de sorte que le résultat final est ordonné selon la séquence des destinataires de transfert.
Un proxy DOIT (MUST) envoyer un champ d'en-tête Via approprié, comme décrit ci-dessous, dans chaque message qu'il transfère. Une passerelle HTTP-to-HTTP DOIT (MUST) envoyer un champ d'en-tête Via approprié dans chaque message de requête entrant et PEUT (MAY) envoyer un champ d'en-tête Via dans les messages de réponse transférés.
Pour chaque intermédiaire, le received-protocol indique le protocole et la version du protocole utilisés par l'expéditeur en amont du message. Ainsi, la valeur du champ Via enregistre les capacités de protocole annoncées de la chaîne requête/réponse de sorte qu'elles restent visibles pour les destinataires en aval ; cela peut être utile pour déterminer quelles fonctionnalités rétro-incompatibles pourraient être sûres à utiliser en réponse, ou dans une requête ultérieure, comme décrit dans la Section 2.5. Pour des raisons de brièveté, le protocol-name est omis lorsque le protocole reçu est HTTP.
La partie received-by est normalement l'hôte et le numéro de port optionnel d'un serveur ou client destinataire qui a ensuite transféré le message. Cependant, si l'hôte réel est considéré comme une information sensible, un expéditeur PEUT (MAY) le remplacer par un pseudonyme. Si un port n'est pas fourni, un destinataire PEUT (MAY) interpréter cela comme signifiant qu'il a été reçu sur le port par défaut, le cas échéant, pour le received-protocol.
Un expéditeur PEUT (MAY) générer des commentaires pour identifier le logiciel de chaque destinataire, analogue aux champs d'en-tête User-Agent et Server. Cependant, les commentaires dans Via sont facultatifs, et un destinataire PEUT (MAY) les supprimer avant de transférer le message.
Par exemple, un message de requête pourrait être envoyé depuis un agent utilisateur HTTP/1.0 vers un proxy interne dont le nom de code est「fred」, qui utilise HTTP/1.1 pour transférer la requête vers un proxy public à p.example.net, qui complète la requête en la transférant au serveur d'origine à www.example.com. La requête reçue par www.example.com aurait alors le champ d'en-tête Via suivant :
Via: 1.0 fred, 1.1 p.example.net
Un intermédiaire utilisé comme portail à travers un pare-feu réseau NE DEVRAIT PAS (SHOULD NOT) transférer les noms et ports des hôtes dans la région du pare-feu à moins qu'il ne soit explicitement activé pour le faire. S'il n'est pas activé, un tel intermédiaire DEVRAIT (SHOULD) remplacer chaque hôte received-by de tout hôte derrière le pare-feu par un pseudonyme approprié pour cet hôte.
Un intermédiaire PEUT (MAY) combiner une sous-séquence ordonnée de membres de liste du champ d'en-tête Via en un seul membre si les entrées ont des valeurs received-protocol identiques. Par exemple,
Via: 1.0 ricky, 1.1 ethel, 1.1 fred, 1.0 lucy
pourrait être réduit à
Via: 1.0 ricky, 1.1 mertz, 1.0 lucy
Un expéditeur NE DEVRAIT PAS (SHOULD NOT) combiner plusieurs membres de liste à moins qu'ils ne soient tous sous le même contrôle organisationnel et que les hôtes n'aient déjà été remplacés par des pseudonymes. Un expéditeur NE DOIT PAS (MUST NOT) combiner des membres qui ont des valeurs received-protocol différentes.
7.7. Transformations de Messages (Message Transformations)
Certains intermédiaires incluent des fonctionnalités pour transformer les messages et leur contenu. Un proxy pourrait, par exemple, convertir entre les formats d'image afin d'économiser de l'espace de cache ou de réduire la quantité de trafic sur une liaison lente. Cependant, des problèmes opérationnels peuvent survenir lorsque ces transformations sont appliquées à du contenu destiné à des applications critiques, telles que l'imagerie médicale ou l'analyse de données scientifiques, en particulier lorsque des contrôles d'intégrité ou des signatures numériques sont utilisés pour garantir que le contenu reçu est identique à l'original.
Un proxy HTTP-to-HTTP est appelé un「proxy de transformation」(transforming proxy) s'il est conçu ou configuré pour modifier les messages d'une manière sémantiquement significative (c'est-à-dire, des modifications, au-delà de celles requises par le traitement HTTP normal, qui changent le message d'une manière qui serait significative pour l'expéditeur d'origine ou potentiellement significative pour les destinataires en aval). Par exemple, un proxy de transformation pourrait agir comme un serveur d'annotation partagé (modifiant les réponses pour inclure des références à une base de données d'annotations locales), un filtre de logiciels malveillants, un transcodeur de format ou un filtre de confidentialité. De telles transformations sont présumées être souhaitées par le client (ou l'organisation cliente) qui a choisi le proxy.
Si un proxy reçoit un URI cible avec un nom d'hôte qui n'est pas un nom de domaine pleinement qualifié, il PEUT (MAY) ajouter son propre domaine au nom d'hôte qu'il a reçu lors du transfert de la requête. Un proxy NE DOIT PAS (MUST NOT) modifier le nom d'hôte si l'URI cible contient un nom de domaine pleinement qualifié.
Un proxy NE DOIT PAS (MUST NOT) modifier les parties「absolute-path」et「query」de l'URI cible reçue lors de son transfert au prochain serveur entrant, sauf si cela est requis par ce protocole de transfert. Par exemple, un proxy transférant une requête à un serveur d'origine via HTTP/1.1 remplacera un chemin vide par「/」(Section 3.2.1 de [HTTP/1.1]) ou「*」(Section 3.2.4 de [HTTP/1.1]), selon la méthode de requête.
Un proxy NE DOIT PAS (MUST NOT) transformer le contenu (Section 6.4) d'un message de réponse qui contient une directive de cache no-transform (Section 5.2.2.6 de [CACHING]). Notez que cela ne s'applique pas aux transformations de messages qui ne modifient pas le contenu, telles que l'ajout ou la suppression de codages de transfert (Section 7 de [HTTP/1.1]).
Un proxy PEUT (MAY) transformer le contenu d'un message qui ne contient pas de directive de cache no-transform. Un proxy qui transforme le contenu d'une réponse 200 (OK) peut informer les destinataires en aval qu'une transformation a été appliquée en changeant le code d'état de réponse à 203 (Non-Authoritative Information) (Section 15.3.4).
Un proxy NE DEVRAIT PAS (SHOULD NOT) modifier les champs d'en-tête qui fournissent des informations sur les points de terminaison de la chaîne de communication, l'état de la ressource ou la représentation sélectionnée (autre que le contenu) à moins que la définition du champ n'autorise spécifiquement une telle modification ou que la modification ne soit jugée nécessaire pour des raisons de confidentialité ou de sécurité.
7.8. Upgrade
Le champ d'en-tête「Upgrade」est destiné à fournir un mécanisme simple pour la transition de HTTP/1.1 vers un autre protocole sur la même connexion.
Un client PEUT (MAY) envoyer une liste de noms de protocole dans le champ d'en-tête Upgrade d'une requête pour inviter le serveur à basculer vers un ou plusieurs des protocoles nommés, par ordre de préférence décroissant, avant d'envoyer la réponse finale. Un serveur PEUT (MAY) ignorer un champ d'en-tête Upgrade reçu s'il souhaite continuer à utiliser le protocole actuel sur cette connexion. Upgrade ne peut pas être utilisé pour insister sur un changement de protocole.
Upgrade = #protocol
protocol = protocol-name ["/" protocol-version]
protocol-name = token
protocol-version = token
Bien que les noms de protocole soient enregistrés avec une casse préférée, les destinataires DEVRAIENT (SHOULD) utiliser une comparaison insensible à la casse lors de la correspondance de chaque protocol-name aux protocoles pris en charge.
Un serveur qui envoie une réponse 101 (Switching Protocols) DOIT (MUST) envoyer un champ d'en-tête Upgrade pour indiquer le ou les nouveaux protocoles vers lesquels la connexion est en train de basculer ; si plusieurs couches de protocole sont en train de basculer, l'expéditeur DOIT (MUST) lister les protocoles dans l'ordre croissant des couches. Un serveur NE DOIT PAS (MUST NOT) basculer vers un protocole qui n'a pas été indiqué par le client dans le champ d'en-tête Upgrade de la requête correspondante. Un serveur PEUT (MAY) choisir d'ignorer l'ordre de préférence indiqué par le client et de sélectionner le ou les nouveaux protocoles en fonction d'autres facteurs, tels que la nature de la requête ou la charge actuelle du serveur.
Un serveur qui envoie une réponse 426 (Upgrade Required) DOIT (MUST) envoyer un champ d'en-tête Upgrade pour indiquer les protocoles acceptables, par ordre de préférence décroissant.
Un serveur PEUT (MAY) envoyer un champ d'en-tête Upgrade dans toute autre réponse pour annoncer qu'il implémente la prise en charge de la mise à niveau vers les protocoles listés, par ordre de préférence décroissant, lorsque cela est approprié pour une requête future.
Voici un exemple hypothétique envoyé par un client :
GET /hello HTTP/1.1
Host: www.example.com
Connection: upgrade
Upgrade: websocket, IRC/6.9, RTA/x11
Les capacités et la nature de la communication au niveau de l'application après le changement de protocole dépendent entièrement du ou des nouveaux protocoles choisis. Cependant, immédiatement après avoir envoyé la réponse 101 (Switching Protocols), le serveur est censé continuer à répondre à la requête d'origine comme s'il avait reçu son équivalent dans le nouveau protocole (c'est-à-dire que le serveur a toujours une requête en cours à satisfaire après le changement de protocole, et est censé le faire sans exiger que la requête soit répétée).
Par exemple, si le champ d'en-tête Upgrade est reçu dans une requête GET et que le serveur décide de changer de protocole, il répond d'abord avec un message 101 (Switching Protocols) en HTTP/1.1, puis suit immédiatement avec l'équivalent du nouveau protocole d'une réponse à un GET sur la ressource cible. Cela permet à une connexion d'être mise à niveau vers des protocoles avec la même sémantique que HTTP sans le coût de latence d'un aller-retour supplémentaire. Un serveur NE DOIT PAS (MUST NOT) changer de protocole à moins que la sémantique du message reçu puisse être honorée par le nouveau protocole ; une requête OPTIONS peut être honorée par n'importe quel protocole.
Voici un exemple de réponse à la requête hypothétique ci-dessus :
HTTP/1.1 101 Switching Protocols
Connection: upgrade
Upgrade: websocket
[... le flux de données bascule vers websocket avec une réponse appropriée
(telle que définie par le nouveau protocole) à la requête「GET /hello」...]
Un expéditeur d'Upgrade DOIT (MUST) également envoyer une option de connexion「Upgrade」dans le champ d'en-tête Connection (Section 7.6.1) pour informer les intermédiaires de ne pas transférer ce champ. Un serveur qui reçoit un champ d'en-tête Upgrade dans une requête HTTP/1.0 DOIT (MUST) ignorer ce champ Upgrade.
Un client ne peut pas commencer à utiliser un protocole mis à niveau sur la connexion tant qu'il n'a pas complètement envoyé le message de requête (c'est-à-dire que le client ne peut pas changer le protocole qu'il envoie au milieu d'un message). Si un serveur reçoit à la fois un champ d'en-tête Upgrade et un champ d'en-tête Expect avec l'attente「100-continue」(Section 10.1.1), le serveur DOIT (MUST) envoyer une réponse 100 (Continue) avant d'envoyer une réponse 101 (Switching Protocols).
Le champ d'en-tête Upgrade s'applique uniquement au changement de protocoles au-dessus de la connexion existante ; il ne peut pas être utilisé pour changer le protocole de connexion (transport) sous-jacent, ni pour basculer la communication existante vers une connexion différente. Pour ces objectifs, il est plus approprié d'utiliser une réponse 3xx (Redirection) (Section 15.4).
Cette spécification définit uniquement le nom de protocole「HTTP」pour une utilisation par la famille de protocoles de transfert hypertexte, tel que défini par les règles de version HTTP de la Section 2.5 et les futures mises à jour de cette spécification. Les noms de protocole supplémentaires devraient être enregistrés en utilisant la procédure d'enregistrement définie dans la Section 16.7.