Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Javascript non-blocking scripts, why don't simply put all scripts before </body> tag?

In order to avoid javascript to block webpage rendering, can't we just put all all our JS files/code to be loaded/executed simply before the closing </body> tag?

All JS files and code would be downloaded and executed only after the all page has being rendered, so what's the need for tricks like the one suggested in this article about non blocking techniques to load JS files. He basically suggests to use code like:

document.getElementsByTagName("head")[0].appendChild(script);

in order to defer script laod while letting the webpage to be rendered, thus resulting in fast rendering speed of the webpage.

But without using this type of non-blocking technique (or other similar techniques), wouldn't we achieve the same non-blocking result by simply placing all our JS files (to be loaded/executed) before the closing </body> tag?

I'm even more surprised because the author (in the same article) suggests to put his code before the closing </body> tag (see the "Script placement" section of the article), so he is basically loading the scripts before the closing </body> tag anyway. What's the need for his code then?

I'm confused, any help appreciated, thanks!


UPDATE

FYI Google Analytics is using similar non-blocking technique to load their tracking code:

<script type="text/javascript">
...
(function() 
{
   var ga = document.createElement('script');
   ga.type = 'text/javascript';
   ga.async = true;
   ga.src = 'your-script-name-here.js';
   var s = document.getElementsByTagName('script')[0];
   s.parentNode.insertBefore(ga, s); //why do they insert it before the 1st script instead of appending to body/head could be the hint for another question.
})();
</script>
</head>
like image 458
Marco Demaio Avatar asked Jul 26 '11 09:07

Marco Demaio


People also ask

Why do you put script tags at the end of the body not in head?

The best practice is to put JavaScript <script> tags just before the closing </body> tag rather than in the <head> section of your HTML. The reason for this is that HTML loads from top to bottom. The head loads first, then the body, and then everything inside the body.

Can you put more than one script tag inside the body tag?

Yes, we can write any number of tags inside tag.

Why is it a good idea to put your JavaScript either with script tags or an external file link near the end of the HTML body instead of in the head of the HTML?

Placing scripts in external files has some advantages: It separates HTML and code. It makes HTML and JavaScript easier to read and maintain. Cached JavaScript files can speed up page loads.

Why is the script tag placed towards the end of the body tag?

Using the script tag to include an external JavaScript file The script tag should either be included between the <head> tags or just before the closing <body> tag in your HTML document. JavaScript is often placed before the closing body tag to help reduce the page loading time.


2 Answers

Generally saying no. Even if scripts will be loaded after all the content of the page, loading and executing of the scripts will block the page. The reason for that is possibility of presence of write commands in your scripts.

However if all you want to achieve is the speed of loading page contents, the result of placing script tags right before </body> tag is the same as for creating script tags dynamically. The most significant difference is that when you load scripts in common static way they are executed one by one, in other words no parallel execution of script file (in old browsers the same true is for downloading of the script too).

like image 110
bjornd Avatar answered Sep 27 '22 17:09

bjornd


If you want asynchonous scripts. Use the (HTML5) async tag if it is availble in the browser you're in. This is what Google Analytics is doing in the code you posted (specifically the line ga.async = true MDN Link, scroll down for async).

However, this can cause your script to load at arbitrary times during the page load - which might be undesirable. It's worth asking yourself the following questions before choosing to use async.

Don't need user input? Then using the async attribute.

Need to respond to buttons or navigation? Then you need to put them at the top of the page (in head) and not use the async tag.

Async scripts run in any order, so if your script is depending on (say) jQuery, and jQuery is loaded in another tag, your script might run before the jQuery script does - resulting in errors.


Why don't people put things at the bottom of the body tag? If the script is taking enough time to load that it's slowing/pausing the load of the website, it's quite possible that that script is going to pause/hang the website after the website has loaded (expect different behaviour on different browsers) - making your website appear unresponsive (click on a button and nothing happens). In most cases this is not ideal, which is why the async attribute was invented.


Alternatively if your script is taking a long time to load - you might want to (after testing) minify and concatenate your script before sending it up to the server.

I recommend using require.js for minifying and concatenation, it's easy to get running and to use.

Minifying reduces the amount of data that needs to be downloaded.

Concatenating scripts reduces the number of "round-trips" to the server (for a far away server with 200ms ping, 5 requests takes 1 second).

like image 41
Griffork Avatar answered Sep 27 '22 16:09

Griffork