SPIP Blog

Du logiciel libre et de la tendresse

Accueil > Développement > Ajax Parallel Loading : accélérer un site SPIP

Ajax Parallel Loading : accélérer un site SPIP

dimanche 6 juin 2010, par cedric

Où l’on découvre une proposition innovante de Facebook pour accélérer les sites Web, qui fait rêver Drupal, et déjà prête à l’emploi dans SPIP. Quand on vous dit de ne pas s’arrêter aux préjugés...

Tout commence par un RT

Cette histoire croustillante commence par un ReTwitt d’un post de Dries Buytaert (pour ceux qui ne suivent pas, le créateur de Drupal) qui apparait dans ma timeline (http://twitter.com/Dries/status/15483730432) :

We should look into a « Facebook BigPipe »-like solution for Drupal 8 : http://bit.ly/9oFLaS #drupal #performance #todolist

Tiens qu’est-ce donc que cette solution magique de Facebook pour améliorer les performances d’un site, et qui intéresse Dries ?

La proposition de Facebook

Ni une, ni deux, je file sur l’article technique (attention, c’est du Facebook dedans, ne cliquez pas si vous tenez à votre vie privée).

En résumé, pour ceux qui n’ont pas activé leur TOR ou ne comprennent pas l’anglais, l’auteur propose de rendre disponible les pages web dans le navigateur plus rapidement en les découpant en morceaux :

  • un morceau ossature principal envoyé au plus vite au visiteur ;
  • plusieurs morceaux de contenu (appelés pagelet), calculés et envoyés séparément.

La page complète est reconstituée dans le navigateur par une fonction javascript.

Ainsi, le rendu et l’interprétation des CSS et JS peuvent démarrer plus tôt dans le navigateur, et la page complète peut être construite par plusieurs processus séparés, en parallèle, sur le serveur.

Mais ça me rappelle quelque chose ...

Intéressant, mais n’ai-je pas l’impression d’avoir déjà vu ça quelque part ?
Ah oui ! A tout seigneur, tout honneur, c’est à Fil que l’on doit la première initiative dans ce sens dans SPIP : http://zone.spip.org/trac/spip-zone/log/_plugins_/inclure-ajaxload

Son plugin inclure-ajaxload permet d’ajouter une condition {ajaxload} sur la balise INCLURE de SPIP.

Le principe ressemble à ce que facebook propose : au lieu d’assembler la page au moment de son calcul, l’inclusion est remplacée par un morceau de javascript envoyé au navigateur, qui va provoquer le chargement du morceau de page séparément de la partie principale de la page.

L’assemblage de la page n’est donc pas réalisée au moment du calcul, côté serveur, mais dans le navigateur, côté client.

Cette première expérimentation était intéressante, mais nécessitait de modifier le squelette pour en bénéficier.

Industrialisons avec Zpip

Le concept de Facebook « une ossature principale qui charge des morceaux de page », cela évoque, pour ceux qui ont commencé à le pratiquer, le concept de Zpip.

On retrouve dans Zpip cette idée d’ossature principale de page, organisée ensuite en blocs de contenus. Sauf que tout est assemblé côté serveur.

Alors justement, je me suis dit qu’il devrait être facile d’automatiser un fonctionnement proche de ce que propose Facebook.

De fait, quelque commit plus tard, Zpip contient une fonctionnalité appelée « Ajax Parallel Loading ».

Le plus intéressant est que cette fonctionnalité ne nécessite aucune modification de squelettes. Il suffit de l’activer par un define pour préciser quels blocs doivent être chargés en parallèle.

Voyons cela en exemple sur SPIP-Contrib. Le site est construit sur la base de Zpip, avec un bloc supplémentaire, nommé « more », qui contient en fait les commentaires en pleine largeur sur les pages d’article.

Ce bloc est ajouté en listant les blocs de Zpip dans une globale :

Ensuite, pour fluidifier le chargement des pages, on indique à Zpip que l’on veut charger les deux blocs ’contenu’ et ’more’ en parallèle du reste de la page :

Tout cela se retrouve dans http://zone.spip.org/trac/spip-zone/changeset/38626

Le résultat est visible directement sur http://www.spip-contrib.net. La page est d’abord chargé avec son ossature, puis le contenu principal, et enfin les forums.

Au final, le temps total de chargement de la page n’est pas plus rapide pour le visiteur, mais il se dégage une impression de fluidité. Au lieu d’attendre devant une roue qui tourne dans son navigateur, il voit tout de suite la page se charger, puis le contenu principal. De plus, ce contenu est disponible plus rapidement car il n’est pas nécessaire d’attendre les forums qui arrivent après, et sont traditionnellement plus lourds et longs à calculer.

Plus intéressant encore, et non évoqué par Facebook, le référencement du site n’est pas dégradé par cette méthode. En effet, les robots indexeur des moteurs de recherche sont connus. Et comme la méthode implémentée par Zpip est automatique, il est facile de leur servir la page complète, avec tout son contenu, au lieu d’une page coquille vide.

On peut donc sans hésiter affirmer que la solution implémentée est sur ce point meilleure que celle évoquée par FaceBook !

SPIP toujours en pointe !

Encore une occasion de démontrer que SPIP reste à la pointe. N’en déplaise aux mauvaises langues qui s’acharnent à le traiter de vieillot, confondant certainement maturité et obsolescence.

Mieux encore, ainsi qu’on avait déjà pu l’aborder à propos des requêtes SQL et de la charge serveur, son architecture interne, basée sur un langage de templating compilé et caché lui procure de nombreux avantages.

Exploitée au mieux par le modèle de squelettes Zpip, cette architecture permet au final des prouesses techniques dans un temps qui doit laisser Dries songeur ...

Messages

  • Merci, c’est brillant !

    SPIP, jai toujours aimé pour plein de raison et je ne comprends pas pourquoi il faut le mettre dans les vieilleries du web ??

    Personnelement, j’ai utilisé plein de solutions CMS (j’en utilise encore quelques uns), et je peux vous assurer que SPIP sur de nombreux aspects est bien équivalent voir supérieur à bien d’autres CMS qui ont le vent en poupe !

    Merci et bon courage...

  • Génial et élégant une fois de plus !

    Il serait intéressant d’ajouter un moyen simple de vérifier que le navigateur est bien capable de traiter du JS, par contre, il n’y a pas que les robots des moteurs de recherche qui en ont besoin...

  • super sauf pour celui qui n’a pas javascript qui se retrouve avec un beau loading et une page vide.

  • Tout à fait, il manque encore la gestion des visiteurs sans javascript. On a des idées, mais faut murir quelque chose de propre, efficace, élégant. Je note que Facebook ne traite pas ce problème là non plus ...

  • sauf que facebook tu peux pas te connecter au site sans js donc tu n’as pas le problème (sauf à le désactiver en cours de route).

  • oui on est bien d’accord :) Ce n’est pas une excuse pour ne pas traiter la question !

  • Bonjour,

    Il serait intéressant d’afficher les performances de Spip en temps de requête et en charge serveur sur une configuration banal avec squelettes-dist et le comparer à Zpip !

    A savoir que l’on peut afficher ses performances sur son propre squelettes en tapant :

    www.monsite.com/spip.php?var_profile

    Et oui Spip n’est pas un vielle écureuil !

    squirrel :)

  • Voilà, APL n’empêche plus ceux qui n’ont pas javascript de voir le site !... (à tester sur SPIP-Contrib, toujours).

  • Et supposons qu’on veuille utiliser le plugin « inclure-ajaxload » donné dans le lien dans ses propres squelettes, il fonctionne actuellement ? Parce que bon là j’ai été le tester pour voir et les requêtes ajax reçoivent comme réponse « signature ajax bloc incorrecte ». Et je ne sais pas du tout comment remédier à cela.

  • Tu peux discuter de ce plugin inclure-ajaxload sur la liste spip-zone@rezo.net ! Je pense que Fil se fera un plaisir de te répondre.

  • Super initiative que l’APL !

    Je viens d’essayer et j’ai notamment un souci qui apparaît avec d’autres scripts jquery :

    Mes scripts se déclenchent au document.ready en cachant des choses (qui vont se dérouler ultérieurement). Or, quand j’utilise APL, tout ces objets cachés lors du document.ready et qui sont dans les blocs chargés ultérieurement sont réaffichés en même temps que le reste du bloc !

    APL déclenche-t-il un évènement javascript (équivalent à document.ready) quand il a fini de charger le bloc, que je puisse cacher mes trucs à déplier ?

  • Il faut utiliser onAjaxLoad(nomdelafonction); pour enregistrer la fonction à exécuter à chaque chargement ajax, et qui sera donc appelée lorsque les blocs arrivent après la page principale.

  • Ah oui ! onAjaxLoad(nomdelafonction); fonctionne bien ! Merci...

    Un petit coup d’œil à Programmer Spip m’a en plus permis de comprendre comment on s’en sert !!

    Génial !

  • « Et comme la méthode implémentée par Zpip est automatique, il est facile de leur servir la page complète, avec tout son contenu, au lieu d’une page coquille vide. »

    IL est facile, c’est à dire ? c’est déjà pris en compte ou c’est quelque chose qui reste à faire :-) ?

  • Les moteurs de recherche et les internautes sans js sont bien pris en charge par APL sans qu’il soit nécessaire de faire quoi que ce soit d’autre que d’activer la fonction.

  • @cédric : merci de cette précision, je vais tester très vite. Je connais un magazine online qui en aurait bien besoin.

  • Il y a une légère erreur de conception dans le plugin “ajaxload” qui empêche la mise en cache du résultat que ce soit coté SPIP ou coté navigateur.

    Il semblerait, d’après mes expérimentations sur mon site internet, que remplacer la requête de type POST par un GET résolve le problème.

  • Les requêtes parallèles sont bien en GET, et pas en POST, ce qui serait en effet une erreur. Donc je ne sais pas où tu as constaté ce défaut.

    Par ailleurs, on constate effectivement que Safari (et chrome aussi il me semble) ne stocke pas les requêtes parallèles et les re-soumet lorsqu’on utiliser le bouton ’back’. Ce n’est pas le cas des autres navigateurs. Ce point reste à traiter (soit par une mise en cache local avec les api html5, soit en exploitant mieux webkit, car il apparait qu’il garde bien, dans certains cas, les modifications de DOM en cache).

  • vouais vouais reste que servir une page spécifique aux robots c’est pas le mieux pour être pote avec, non ?

  • @pi_r ca dépend ! Si tu le fais comme un goret, tu vas te faire gicler oui ! Là la méthode reste propre. Quand à Google spécifiquement, ce qu’il n’aime pas ce sont les variantes dans le contenu, pas dans le conteneur, ca il s’en fout (enfin logiquement, parce que rien n’est jamais vraiment certain avec Big G ;) )

Un message, un commentaire ?

Qui êtes-vous ?
Se connecter
Votre message

Ce formulaire accepte les raccourcis SPIP [->url] {{gras}} {italique} <quote> <code> et le code HTML <q> <del> <ins>. Pour créer des paragraphes, laissez simplement des lignes vides.