Maison >interface Web >js tutoriel >Solution d'optimisation des performances de chargement non bloquante en compétences JavaScript_javascript

Solution d'optimisation des performances de chargement non bloquante en compétences JavaScript_javascript

WBOY
WBOYoriginal
2016-05-16 16:34:371309parcourir

Les performances de Javascript dans le navigateur peuvent être considérées comme le problème d'utilisabilité le plus important auquel sont confrontés les développeurs front-end.

Parmi les règles Yslow 23 de Yahoo, l’une d’elles consiste à mettre JS en bas. La raison en est qu'en fait, la plupart des navigateurs utilisent un seul processus pour gérer plusieurs tâches telles que l'interface utilisateur et la mise à jour de Javascript, et qu'une seule tâche peut être exécutée à la fois. Combien de temps le Javascript est-il exécuté, puis combien de temps il attend avant que le navigateur ne devienne inactif pour répondre à l'interaction de l'utilisateur.

À un niveau de base, cela signifie que la présence de la balise <script> fait attendre la page entière que le script soit analysé et exécuté. Que le code JavaScript réel soit en ligne ou contenu dans un fichier externe non lié, le processus de téléchargement et d'analyse de la page doit s'arrêter et attendre que le script termine ce traitement avant de continuer. Il s'agit d'une partie essentielle du cycle de vie de la page, puisque les scripts peuvent modifier le contenu de la page lors de son exécution. Un exemple typique est la fonction document.write(), par exemple : <br> </p> <div class="codetitle"> <span><a style="CURSOR: pointer" data="5199" class="copybut" id="copybut5199" onclick="doCopy('code5199')"><u>Copier le code</u></a></span> Le code est le suivant :</div> <div class="codebody" id="code5199"> <br> <html><br> <tête><br> <title>Exemple de script</title><br> </tête> <br> <corps><br> <p><br>             <script type="text/javascript"><br>                  document.write("La date est " (new Date()).toDateString());<br>                                                                                             </p><br> </corps> </html><br> <br><br> Lorsque le navigateur rencontre une balise <script>, comme dans la page HTML ci-dessus, il n'y a aucun moyen de prédire si JavaScript ajoutera du contenu dans la balise <p> Par conséquent, le navigateur s'arrête, exécute ce code JavaScript, puis continue l'analyse et la traduction de la page. La même chose se produit lors du chargement de JavaScript à l'aide de l'attribut src. Le navigateur doit d'abord télécharger le code du fichier externe, ce qui prend un certain temps, puis analyser et exécuter le code. Au cours de ce processus, l'analyse des pages et l'interaction de l'utilisateur sont complètement bloquées. <br> </div>Étant donné que les scripts bloquent le processus de téléchargement d'autres ressources de la page, l'approche recommandée consiste à placer toutes les balises <script> aussi près que possible du bas de la balise <body> page. Par exemple : <br> <p><br></p> <div class="codetitle">Copier le code<span><a style="CURSOR: pointer" data="96913" class="copybut" id="copybut96913" onclick="doCopy('code96913')"><u> Le code est le suivant :</u></a></span> <html></div> <tête><div class="codebody" id="code96913"> <title>Exemple de script</title><br> <link rel="stylesheet" type="text/css" href="styles.css"> </tête><br> <br> <corps><br> <p>Bonjour tout le monde !</p><br> <-- Exemple de positionnement de script recommandé --->           <script type="text/javascript" src="file1.js"></script>                    




Ce code indique l'emplacement recommandé de la balise <script> Bien que les téléchargements de scripts se bloquent, la page a été téléchargée et affichée devant l'utilisateur, et la vitesse d'accès à la page ne sera pas trop lente. C'est ce qui a été mentionné ci-dessus concernant la mise de JS en bas. <br> <br>De plus, Yahoo! crée un « handle syndical » pour sa bibliothèque « Yahoo! User Interface (YUI) », qui est implémentée via leur « Content Delivery Network (CDN) » de. N'importe quel site Web peut utiliser une URL « union handle » pour indiquer quels fichiers du package YUI sont inclus. Par exemple, l'URL suivante contient deux fichiers : <br> <br><br> </div>Copier le code<p></p> <p> Le code est le suivant :<br></p> <div class="codebody" id="code74887"> <br> <script type="text/javascript" src="http://yui.yahooapis.com/combo?2.7.0/build/yahoo/yahoo-min.js&2.7.0/build/event/event-min.js "></script>

Cette URL appelle la version 2.7.0 des fichiers yahoo-min.js et event-min.js. Ces fichiers sont deux fichiers distincts sur le serveur, mais lorsque le serveur reçoit cette demande d'URL, les deux fichiers seront fusionnés et renvoyés au client. De cette façon, il n'est pas nécessaire d'avoir deux balises <script> (chacune chargeant un fichier), et une balise <script> C'est la meilleure façon d'inclure plusieurs Javascripts externes dans une page HTML. </p> <p><strong>Scripts non bloquants Scripts non bloquants</strong></p> <p>Ce qui précède est le meilleur moyen de charger plusieurs scripts Javascript dans l'état initial de la page. Javascript a tendance à bloquer certains processus du navigateur, tels que les requêtes http et les actualisations de l'interface, ce qui constitue le problème de performances le plus important auquel sont confrontés les développeurs. Garder les fichiers JavaScript courts et limiter le nombre de requêtes http ne sont que les premières étapes de la création d'applications Web réactives. </p> <p>Mais comme pour les grandes pages Web contenant beaucoup de code JS, garder le code source court n'est pas toujours le meilleur choix. Ainsi, des scripts non bloquants ont vu le jour. Ce dont nous avons besoin, c'est d'ajouter progressivement du javascript à la page sans bloquer dans une certaine mesure le navigateur. </p> <p>La clé pour ne pas bloquer le script est d'attendre la fin du chargement de la page avant de charger le code source Javascript, ce qui signifie commencer à télécharger le code après l'émission de l'événement de chargement de la fenêtre. </p> <p>Explication connexe : </p> <p>L'événement de chargement de la fenêtre ne sera déclenché qu'une seule fois et une seule fois après le chargement de la page. <br> window.onload=function(){} doit attendre que tout le contenu de la page Web soit chargé (y compris tous les fichiers associés à l'élément, tels que les images) avant de pouvoir être exécuté. Autrement dit, Javascript ne peut accéder qu'à n'importe quel élément. la page à ce moment. </p> <p>Plusieurs méthodes sont les suivantes : </p> <p><strong>Scripts différés Scripts différés</strong></p> <p>Html4 définit un attribut étendu pour la balise <script> </p> <p>Cet attribut defer indique que le script contenu dans l'élément n'est pas destiné à modifier le DOM, le code peut donc être exécuté ultérieurement. L'attribut defer n'est pris en charge que par Internet Explorer 4 et Firefox 3.5, ce qui n'en fait pas une solution multi-navigateurs idéale. Sur les autres navigateurs, l'attribut defer sera ignoré. Par conséquent, la balise <script> sera traitée de la manière normale par défaut, ce qui entraînera un blocage. Si elle est prise en charge par tous les principaux navigateurs, cette solution reste efficace. <br> </p> <div class="codetitle"> <span><a style="CURSOR: pointer" data="14408" class="copybut" id="copybut14408" onclick="doCopy('code14408')"><u>Copier le code</u></a></span> Le code est le suivant :</div> <div class="codebody" id="code14408"> <br> <script type="text/javascript" src="file1.js" defer></script>

Une balise <script> avec un attribut defer peut être placée n'importe où dans le document et lancera le téléchargement au fur et à mesure de son analyse jusqu'à ce que le DOM soit chargé (avant que le gestionnaire d'événement onload ne soit appelé). Lorsqu'un fichier Javascript différé est téléchargé, il ne bloque pas les autres traitements du navigateur, les fichiers peuvent donc être téléchargés en parallèle avec d'autres ressources. </p> <p>Vous pouvez utiliser le code suivant pour tester si le navigateur prend en charge l'attribut defer : <br> </p> <div class="codetitle"> <span><a style="CURSOR: pointer" data="95845" class="copybut" id="copybut95845" onclick="doCopy('code95845')"><u>Copier le code</u></a></span> Le code est le suivant :</div> <div class="codebody" id="code95845"> <br> <html><br> <tête><br> <title>Exemple de report de script</title><br> </tête> <br> <corps><br> <script différer> alert("différer");</script> <script> alerte("script"); </script> <script> window.onload = function(){ alert("load");}; </script>




Si le navigateur ne prend pas en charge le report, l'ordre des boîtes de dialogue contextuelles est "defer", "script", "load".

Si le navigateur prend en charge le report, l'ordre des boîtes de dialogue contextuelles est "script", "load", "defer".

Éléments de script dynamiques Éléments de script dynamiques

DOM nous permet d'utiliser Javascript pour créer dynamiquement presque tout le contenu du document en HTML. Un nouvel élément <script> peut être créé très facilement via le DOM standard : <strong> </strong></p> <p></p> <p>Copier le code</p> <div class="codetitle"> <span><a style="CURSOR: pointer" data="78091" class="copybut" id="copybut78091" onclick="doCopy('code78091')"> Le code est le suivant :<u></u></a> 1 var script = document.createElement ("script");</span> 2 script.type = "texte/javascript";</div> 3 script.src = "file1.js"; <div class="codebody" id="code78091"> 4 document.body.appendChild(script);<br> <br> <p>Le nouvel élément <script> charge le fichier source file1.js. Ce fichier commence à se télécharger dès que l'élément est ajouté à la page. Le point clé de cette technologie est que quel que soit l’endroit où le téléchargement est lancé, le fichier est téléchargé et exécuté sans bloquer le traitement des autres pages. </p> <p>Lorsqu'un fichier est téléchargé à l'aide d'un nœud de script dynamique, le code renvoyé est généralement exécuté immédiatement (sauf pour Firefox et Opera, qui attendront que tous les nœuds de script dynamique précédents terminent leur exécution). </p> <p>Dans la plupart des cas, nous espérons appeler une fonction pour télécharger dynamiquement des fichiers Javascript. Le package de fonctions suivant implémente l'implémentation standard et l'implémentation IE : </p> <p></p> <div class="codetitle"> <span><a style="CURSOR: pointer" data="4795" class="copybut" id="copybut4795" onclick="doCopy('code4795')"><u>Copier le code</u></a></span> Le code est le suivant :</div> <div class="codebody" id="code4795"> <br> fonction loadScript(url, rappel){<br> var script = document.createElement ("script") ;<br> ​ script.type = "text/javascript";<br>        <br> Si (script.readyState){ //IE<br>            script.onreadystatechange = function(){<br> Si (script.readyState == "chargé" || script.readyState == "complete"){<br>               script.onreadystatechange = null;<br>               rappel(); <br>            }<br>         };<br>         } <br>         else { //Autres<br>           script.onload = function(){ callback();<br> }; <br> ><br> Script.src = url;<br> Document.getElementsByTagName("head")[0].appendChild(script); ><br> <br> loadScript("file1.js", function(){ //Appel<br> alert("Le fichier est chargé !"); <br> });<br> <br> </div> Cette fonction accepte deux paramètres : l'URL du fichier Javascript et une fonction de rappel qui se déclenche lorsque la réception Javascript est terminée. L’inspection de la propriété est utilisée pour décider quels événements surveiller. La dernière étape est l'attribut src et l'ajout du fichier javascript à l'en-tête. <p> </p>Le chargement de script dynamique est le mode le plus couramment utilisé dans les téléchargements Javascript non bloquants, car il fonctionne sur tous les navigateurs et est simple et facile à utiliser. <p> </p> <p>Injection de script XMLHttpRequest Injection de script XHR<strong></strong> </p>Une autre façon d'obtenir des scripts de manière non bloquante consiste à utiliser un objet XMLHttpRequest (XHR) pour injecter le script dans la page. Cette technique crée d'abord un objet XHR, puis télécharge le fichier Javascript, puis utilise un élément <script> dynamique pour injecter le code Javascript dans la page. Regardez la démo : <p> </p> <p></p> <div class="codetitle"><span><a style="CURSOR: pointer" data="24685" class="copybut" id="copybut24685" onclick="doCopy('code24685')">Copier le code<u></u></a> Le code est le suivant :</span></div> <div class="codebody" id="code24685"> var xhr = new XMLHttpRequest(); <br> xhr.open("get", "file1.js", true); xhr.onreadystatechange = fonction(){<br> Si (xhr.readyState == 4){<br> If (xhr.status >= 200 && xhr.status < 300 || xhr.status == 304){ // Vérifiez le code d'état http <br>         var script = document.createElement("script"); <br>           script.type = "text/javascript";<br>            script.text = xhr.responseText;<br>              document.body.appendChild(script);<br>          } <br> ><br> }; <br> xhr.send(null);<br> <br> <p>Ce code envoie une requête d'obtention de fichier au serveur pour obtenir file1.js. Le gestionnaire d'événements onreadystatechange vérifie si readyState est 4, puis vérifie si le code d'état http est valide (200 indique que la demande du client a réussi, 2xx indique une réponse valide et 304 indique une réponse mise en cache). Si une réponse valide est reçue, un nouvel élément <script> est créé et son attribut text est défini sur la chaîne ResponseText reçue du serveur. Cela créera en fait un élément <script> avec du code en ligne, et une fois le nouvel élément <script> ajouté au document, le code sera exécuté et prêt à être utilisé. </p> <p>L'avantage de cette méthode est qu'elle a une bonne compatibilité et que vous pouvez télécharger du code Javascript qui n'est pas exécuté immédiatement. Étant donné que le code est renvoyé en dehors de la balise <script>, il ne s'exécutera pas automatiquement après le téléchargement, ce qui vous permettra de différer son exécution. </p> <p>La détermination de cette méthode est soumise à la même restriction d'origine du navigateur. Le fichier Javascript doit être placé dans le même domaine que la page et ne peut pas être téléchargé depuis le CDN (Content Delivery Network). Pour cette raison, les grandes pages Web n’utilisent généralement pas la technologie d’injection de script XHR. </p> <p><strong>Modèle non bloquant recommandé Modèle non bloquant recommandé</strong></p> <p>La méthode recommandée pour charger de grandes quantités de Javascript dans une page est un processus en deux étapes : </p> <p>La première étape inclut le code requis pour charger dynamiquement Javascript, puis charge les parties autres que Javascript requises pour l'initialisation de la page. Cette partie du code doit être aussi petite que possible et ne peut contenir que la fonction loadScript(). Elle se télécharge et s'exécute très rapidement et ne causera pas beaucoup d'interférences avec la page. </p> <p>La deuxième étape, lorsque le code initial est prêt, utilisez-le pour charger le reste du Javascript. </p> <p>Par exemple : <br> </p> <div class="codetitle"> <span><a style="CURSOR: pointer" data="91573" class="copybut" id="copybut91573" onclick="doCopy('code91573')"><u>Copier le code</u></a></span> Le code est le suivant :</div> <div class="codebody" id="code91573"> <br> 1 <script type="text/javascript" src="loader.js"><br> 2 </script>


Placez ce code avant la balise fermante de body . L'avantage de ceci est que, tout d'abord, cela garantit que l'exécution de Javascript n'affectera pas l'affichage d'autres parties d'autres pages. Deuxièmement, lorsque la deuxième partie du fichier Javascript est téléchargée, tout le DOM nécessaire à l'application a été créé et est prêt à être consulté, évitant ainsi l'utilisation de traitements événementiels supplémentaires (tels que window.onload) pour savoir si la page est prêt. .

Une autre option consiste à intégrer la fonction loadScript() directement dans la page, ce qui peut réduire la surcharge d'une requête http. Par exemple :

Copier le code Le code est le suivant :

1

Une fois le code d'initialisation de la page téléchargé, vous pouvez également utiliser la fonction loadScript() pour charger des fonctions supplémentaires requises par la page.

Présentant un outil commun, Ryan Grove de Yahoo! Search a créé la bibliothèque LazyLoad (voir :

http://github.com/rgrove/lazyload/ ). LazyLoad est une puissante fonction loadScript(). LazyLoad ne fait qu'environ 1,5 Ko après minification. Les exemples d'utilisation sont les suivants :

Copier le code Le code est le suivant :



Résumé

1. Placez toutes les balises