Voir et modifier les en-têtes HTTP

Astuce par (Lyon, France)
Créé le , mis à jour le (71610 lectures)
Tags : web, MIME, http, content-type, charset, en-tête, headers

Le protocole HTTP (HyperText Transfer Protocol) est à la base du Web, mais il est très mal connu de beaucoup d’intégrateurs ou développeurs web… et moins bien connu encore des débutants. Nous allons voir ensemble brièvement ce que sont les en-têtes HTTP (HTTP Headers), quels sont les incontournables et comment on peut les modifier.

C’est quoi un en-tête HTTP?

Lorsqu’un serveur web envoie un document (page HTML, fichier texte, image ou autre) à un navigateur web, il n’envoie pas uniquement le contenu du fichier. Il commence par envoyer plusieurs informations sur le fichier. Par exemple, quand vous affichez la source d’une page HTML dans votre navigateur, vous obtenez quelque chose qui ressemble à ceci:

<!doctype html>
<html lang="fr">
  <meta charset="utf-8">
  <title>Salut, ça va?</title>
  ...

Mais en réalité, le navigateur reçoit ceci:

HTTP/1.1 200 OK
Date: Sat, 20 Nov 2010 13:37:00 GMT
Content-Length: 2644
Content-Type: text/html; charset=utf-8
Content-Language: fr

<!doctype html>
<html lang="fr">
  <meta charset="utf-8">
  <title>Salut, ça va?</title>
  ...

La première ligne indique le protocole utilisé et sa version (HTTP 1.1), ainsi que le code de statut HTTP (Wikipédia). Les codes de statut, vous en connaissez déjà certains: 200 pour dire «tout va bien», 404 pour un document non trouvé, 500 pour une erreur serveur, etc. (Si une petite ampoule s’est allumée dans votre tête et que vous vous êtes dit «Ah mais alors c’est ça une erreur 404!», allez jeter un œil à l’article de Wikipédia pour plus d’infos.)

À partir de la deuxième ligne, on a (enfin!) nos en-têtes HTTP. La syntaxe est la suivante: Nom-Entete: valeur, avec un en-tête par ligne. Et après les en-têtes, on a une ligne vide qui marque la séparation entre les méta-données HTTP et le contenu envoyé (code HTML, CSS, JavaScript, fichier texte, fichier binaire de type image ou vidéo ou autre…).

Accéder aux en-têtes HTTP

Le mode «voir la source» des navigateur ne montre pas les en-têtes HTTP, ou le code de statut HTTP. Comment faire alors pour les consulter? Il y a plusieurs moyens:

  • En utilisant les outils pour développeur intégrés au navigateur ou encore Firebug pour Firefox (onglet «Réseau» ou «Ressources» suivant l’outil).
  • En utilisant une extension telle que Web Developer pour Firefox.
  • En utilisant un outil en ligne, par exemple Web Sniffer.

Modifier les en-têtes HTTP

Il existe trois moyens de modifier les en-têtes HTTP envoyés par le serveur web:

  1. En modifiant la configuration globale du serveur web. (Rarement possible sur un hébergement de site web «classique», c’est-à-dire mutualisé.)
  2. En modifiant la configuration locale du serveur web, par exemple dans un fichier .htaccess.
  3. En utilisant un langage côté serveur, par exemple PHP.

Dans les paragraphes qui suivent je passe sur la première et la troisième options. (Si vous souhaitez modifier des en-têtes HTTP en PHP ou autre langage, renseignez-vous, lisez la doc.) Je donnerais uniquement des exemples de directives Apache qui peuvent être utilisées dans un fichier .htaccess.

Type de média avec Content-Type

L’en-tête Content-Type permet de déclarer le type MIME ou type de média du fichier. Les types de média sont standardisés, on a par exemple text/html pour du HTML, application/xhtml+xml pour du XHTML, text/css pour du CSS, image/png et ainsi de suite. Il est important d’envoyer le bon type de média pour chaque fichier que le serveur envoie. Les navigateurs web peuvent refuser d’interpréter ou d’utiliser un fichier envoyé avec un type de média erroné.

Vous pouvez modifier le type MIME envoyé pour un fichier en fonction de son extension, avec la directive Apache AddType. En général le serveur web est bien configuré et on n’a pas besoin de modifier le type de média pour les extensions «classiques», par contre ça peut être nécessaire pour des fichiers audio ou vidéo utilisés avec les éléments audio et video en HTML5 et dans d’autres cas de figure pas très courants.

AddType text/html .html .htm
AddType application/xhtml+xml .xhtml
AddType text/css .css

Codage de caractères avec… Content-Type aussi

Pour des raisons historiques, il n’y a pas d’en-tête séparé pour déclarer le codage des caractères des documents texte. C’est l’en-tête Content-Type qui est utilisé, et l’information sur le codage de caractères est rajoutée après le type de média. Dans notre exemple ça donnait ceci:

Content-Type: text/html; charset=utf-8

Le plus souvent, les serveurs ne déclarent pas de codage de caractères par défaut. Mais mieux vaut rajouter cette information lorsque c’est possible pour votre site. Par exemple si votre site est entièrement en UTF-8 (et votre site est bien entièrement en UTF-8, n’est-ce pas?), vous pouvez ajouter dans un fichier .htaccess à la racine du site:

AddDefaultCharset "utf-8"

Langue primaire du document avec Content-Language

Cet en-tête permet d’indiquer la ou les langue(s) du public visé. La plupart du temps on n’indiquera qu’une seule langue. Avec Apache on peut utiliser la directive DefaultLanguage. Voici deux exemples:

DefaultLanguage "en-AU"
DefaultLanguage "fr, de"

Le premier exemple correspond à un site anglophone qui s’adresse essentiellement à un public australien (par exemple un site gouvernemental). Le deuxième exemple correspond à un site bilingue qui présente aussi bien des contenus en français que des contenus en allemand, sans les séparer (pas de mécanisme de choix de la langue, de bascule entre version française et version allemande). Ce deuxième cas de figure est beaucoup plus rare.

Plus d’en-têtes encore…

Nous n’allons pas détailler les autres en-têtes HTTP existant. En dehors de ceux que nous venons de voir, les plus importants sont ceux qui définissent la mise en cache des fichiers par les navigateurs. C’est un sujet à part entière, très technique, que nous n’allons pas aborder ici; on pourra lire ce tutoriel en anglais ou sa traduction française (pas tout à fait à jour).

Des en-têtes HTTP… dans le code HTML

Pour finir, notez que HTML permet de donner la même information qu’une en-tête HTTP dans le code HTML lui-même, en utilisant l’élément meta. Un exemple classique:

<meta http-equiv="Content-Type" content="text/html; charset=utf-8">

On recommande en général de donner une information sur le codage des caractères dans le code HTML lui-même, en plus de l’en-tête HTTP Content-Type. On peut donc reprendre l’exemple ci-dessus (pour déclarer de l’UTF-8), ou en HTML5 préférer une forme plus courte: <meta charset="utf-8">.

Reprendre les autres en-têtes HTTP dans des balises META est par contre le plus souvent inutile. (Pour plus d’informations sur ce sujet, lire À quoi servent les balises META?.)

Commentaires

Victor BRITO a dit le

Pour accéder aux en-têtes HTTP, il est également possible d'utiliser la fonction PHP get_headers ().

Skoua a dit le

Intéressant. Est-ce que c'est vraiment nécessaire de déclarer l'encodage des caractères dans les headers côté serveur ?
Je n'ai jamais vraiment eu de problème de ce côté-là même si je ne le fais jamais.

Florent V. a dit le

@Skoua, à partir du moment où tu déclares cette info dans le HTML avec une meta http-equiv, les navigateurs s’en sortent très bien. Mais vu qu’il s’agit d’une balise meta de type "http-equiv" (équivalent d'en-tête HTTP), autant être cohérent et avoir cette information directement dans les en-têtes HTTP. Par ailleurs, pour les fichiers non HTML c’est indispensable (je pense notamment aux fichiers JavaScript qui peuvent contenir des chaines de caractères). Donc autant le faire pour tous les fichiers (tu déclares tout en UTF-8 et c’est réglé). Partant de là, c’est la balise META qui est redondante et inutile. :)

Skoua a dit le

@Florent V. : En effet c'est pratique pour les autres types de fichiers je n'y avais pas pensé.
Du coup si je mets l'encodage en UTF-8 dans mon .htaccess je n'ai plus besoin de définir l'encodage dans le html ?
J'imagine que oui mais je veux être sûr, vu le comportement inégal de la plupart des naivgateurs...

Florent V. a dit le

«Du coup si je mets l'encodage en UTF-8 dans mon .htaccess je n'ai plus besoin de définir l'encodage dans le html ?»
Oui. D’ailleurs HTML4 dit clairement que le codage défini dans les en-têtes HTTP est prioritaire sur celui déclaré dans la page HTML, ce qui à ma connaissance est respecté par tous les navigateurs.

Nico3333fr a dit le

De mémoire (j'avais vu le conseil sur le validateur du w3c), c'est bien de préciser les deux pour l'encodage (HTTP et HTML, même si effectivement le header HTTP est prioritaire par rapport au HTML), pour le cas où la page soit enregistrée : comme il n'y a plus de header HTTP sur une version locale, c'est toujours bon que l'encodage soit précisé dans le fichier HTML lui-même.

arnolem a dit le

Pour ceux qui ne voit pas l'intérêt du .htaccess. Sachez qu'il permet de définir l'encodage pour les sorties HTML mais également pour les autres type de fichiers (XML, JSON, CSS, JS, ...)