Skip to Content

Nous adressons toutes nos pensées à la famille de notre ami Jérôme !

http://www.forumsig.org/showthread.php/43488-Disparition-de-Phoenix

Optimiser son site web en réduisant la bande passante


Nous allons nous intéresser aujourd'hui à un des moyens les plus efficaces pour augmenter la fluidité d'une application web : réduire la bande passante.

Pour cela, nous allons voir 3 moyens différents mais complémentaires. Les exemples donnés seront sous web serveur Apache (même s'ils sont à priori extrapolables aux autres serveurs web). Ces 3 moyens sont simples et rapides à mettre en place même si le 3ème point doit être utilisé avec recul.

Ces méthodes ne sont pas spécifiques au webmapping mais peuvent s'appliquer sur n'importe quel site web.

Pour illustrer ces méthodes, je prendrai l'exemple d'un module web personnel basé sur l'utilisation des librairies JavaScript openlayers, ext js (3.4.0) et geoext. Cet exemple, outre le chargement des librairies JavaScript, charge 14 fichiers JavaScript (un générique au site entier, les 13 autres spécifiques au module).

Voici donc un apercu du chargement (grâce à firebug et uniquement pour les fichiers JavaScript) avant  l'utilisation de ces méthodes.

On a donc un total de 19 fichiers JavaScript chargés (5 pour les librairies, 1 général au site et 13 pour ce module) pour un poids total fort conséquent de 1,7 MB qui ralentit forcément l'expérience utilisateur.

Heureusement pour moi, des moyens simples sont à mettre en oeuvre pour contrer cela.

1) la minification des codes clients (JavaScript, html, css...).

La minification est une opération très simple qui consiste à réduire le poids global des fichiers demandés par le client. Pour cela, il suffit de supprimer des espaces inutiles ainsi que des sauts de lignes, tabulations et commentaires, voire de changer des noms de variables et de fonctions (ma_variable devient v1 par exemple). Il existe de nombreux utilitaires pour le faire dont par exemple YUI Compressor (yahoo) ou Google Closure Compiler.

Une fois mes 13 fichiers de module passés au minifieur (Google Closure Compiler, sans changement de noms de variables ou de fonctions), je ramène le poids de 120ko à 86,2 ko.

C'est donc une diminution non négligeable mais vu le poids des librairies JavaScript incluses (qui elles sont évidemment déjà minifiées dans leurs versions de production), l'apport n'est pas énorme.

Pour un petit site, ce n'est donc pas forcément la peine de faire l'effort de  passer par cette étape, d'autant que les 2 prochaines étapes ont un gain plus important.

Par contre, vous voyez que dans mon exemple, je demande 19 fichiers javascript au serveur soit un nombre de requête conséquent. Or, les 13 fichiers de mon module (les 13 derniers chargés) sont séparés uniquement pour pouvoir avoir un code logiquement découpés. Mais n'ayant aucun autre interêt à laisser le code découpé en autant de fichiers, c'est une excellente pratique en terme de performances de fusionner les fichiers qui n'ont pas de raisons d'être séparés.

Et voilà, j'ai réduit le nombre de requête au serveur pour le chargement des fichiers JavaScript de 19 à 7.

La minification peut aussi s'appliquer à d'autres formats comme le html, le css, le xml mais aussi le json et donc le geojson.

Les 2 prochaines méthodes seront à mettre en place dans des fichiers .htaccess ou directement dans la configuration de apache.

Les .htaccess sont donc des fichiers qui contiennent des réglages apache locaux. Si vous placez un .htaccess dans un dossier accessible par le web, il sera systématiquement interprété (sauf chez certains rares hébergeurs) quelque soit la page ou le fichier appelé (dans ce dossier et ses sous-dossiers). Le htaccess permet par exemple de mettre en place une authentification globale.

La méthode des htaccess a le mérite d'être "portable" et modulable (on peut en placer un différent dans chaque répertoire accessible par le web).

2) la compression des contenus entre votre site et le navigateur client.

Il s'agit de compresser les contenus qui peuvent l'être avant envoi au client. Le client décompresse alors le contenu avant de l'interprêter.

L'immense majorité des navigateurs web récents est compatible.

Il vous faut activer le mode deflate sur votre serveur Apache (cf. l'article d'alsacréation en source). Une fois activé, vos contenus de type css, js, html seront compressés avant envoi au navigateur.

Vous pouvez paramétrer finement le comportement du mode deflate dans les htaccess (ne l'activez pas sur les contenus qui sont déjà compressés, les images par exemple !).

SetOutputFilter DEFLATE
AddOutputFilterByType DEFLATE text/html text/css text/plain text/xml application/x-javascript application/json

Voilà ci dessus un exemple de réglage du mode deflate dans un htaccess. Ici vous voyez que j'active le mode deflate pour les types html, text, css, js, xml et json.

Et voilà le résultat : une diminution par 4 de la bande passante pour le chargement des fichiers JavaScript ! La diminution est comparable pour les autres types mime utilisés par mon application (css, html, xml, json, geojson).

3) les directives de mises en cache

Il s'agit ici de mettre en place des directives indiquant au client (navigateur web) s'il peut mettre en cache des fichiers et comment.

Il faut bien que vous gardiez à l'esprit que ce sont des directives données au client mais que celui-ci fait ce qu'il veut.

Les directives peuvent être de plusieurs natures :

  • Interdiction de mise en cache
  • Mettre en cache mais demander systématiquement au serveur si le fichier a été modifié
  • Mettre en cache avec une durée de validité

Attention, ces directives doivent être pensées avec soin sous peine d'avoir des comportements inattendus (utilisation par le navigateur d'un fichier js du cache alors que le fichier js du serveur a considérablement été modifié par exemple). 

Sur mon site, les directives sont différentes selon les dossiers.

Par exemple, les librairies JavaScript sont stockées dans un dossier qui ne sert qu'à ça. Dans ce dossier, le htaccess demande une mise en cache avec une validité énorme (plusieurs mois). Ce type d'instruction est risqué puisque ca veut dire qu'un navigateur peut ne pas demander un fichier pendant plusieurs mois. D'où le fait que je mette cette directive uniquement dans le dossier des librairies JavaScript et avec une subtilité importante : les dossiers de librairies comportent dans leur nom le numéro de version. En effet, sinon, une mise à jour de librairie pourrait ne pas être répércutée au client.

Voilà mes directives de mise en cache pour ce dossier (dans le htaccess du dossier).

<IfModule mod_headers.c>
    <FilesMatch "\\.(ico|jpe?g|png|gif|css|js)$">
        Header set Cache-Control "max-age=999999, public"
    </FilesMatch>
</IfModule>

J'utilise le module headers (gestion des entêtes) pour gérer la mise en cache.

Ici, les fichiers ico, jpg, jpeg, png, gif, css et js sont déclarés comme pouvant être mis en cache pendant 999999 secondes. Une telle directive doit être réservée à des éléments ne bougeant jamais !

Et voilà donc un 2ème exemple sur le répertoire contenant les ressources web spécifiques de mon application.

<IfModule mod_headers.c>
    <FilesMatch "\\.(ico|jpe?g|png|gif)$">
        Header set Cache-Control "max-age=36000, public"
    </FilesMatch>

   <FilesMatch "\\.(ogg)$">
        Header set Last-Modified

  </FilesMatch>

    <FilesMatch "\\.(js|css|json|geojson)$">
        Header set Cache-Control "max-age=3600, public"
    </FilesMatch>
    <FilesMatch "\.(php|php5)$">
        Header unset Cache-Control
    </FilesMatch>
</IfModule>

Une petite explication donc. Ici les fichiers images ne changent presque jamais et s'ils changent n'ont qu'un impact visuel. La directive de mise en cache autorise donc une mise en cache pour 10 heures.

Par contre les fichiers ogg concernent des vidéos susceptibles d'être modifiées à n'importe quel moment d'où la directive de mise en cache avec demande au serveur d'une éventuelle modification.

Les fichiers javascript, css, json et geojson sont déclarés pouvant être mis en cache pendant 1 heure. En effet, bien que modifiables, les éventuelles modification sont mises en place pendant la nuit.

Enfin, les fichiers php sont déclarés comme ne pouvant pas être mis en cache (et c'est normal puisqu'ils génèrent du contenu dynamique que ce soit du html, du xml, du json ou du geojson).

Et voilà, faites bien attention avec ces directives de mise en cache et n'oubliez pas que ce ne sont que des directives, le client gère son cache comme il le souhaite (par exemple, j'ai réglé mon firefox pour qu'il vide son cache à chaque fermeture).

En tout cas, ces directives sont indispensables pour la fluidité et permettent par exemple d'éviter que des contenus soient redemandés au serveur à chaque chargement de page (javascript, css, images...). D'ailleurs, les serveurs ont la plupart du temps des directives de mise en cache par défaut.

 

Un exemple avec la directive last-modified où on voit que les fichiers JavaScript étaient déjà en cache et n'avaient pas été modifiés sur le serveur.

NB : ne faites pas attention au temps de chargement annoncé sur les imprimes-écran firebug, ils dépendaient de la charge du serveur et pas uniquement des opérations d'optimisation effectuées ;)


Site officiel : Apache : cache
Site officiel : Apache : deflate
Autres Liens : Un très bon article sur alsacréations

Commentaires

Poster un nouveau commentaire

Le contenu de ce champ sera maintenu privé et ne sera pas affiché publiquement.