Why scripts at the end of body tag

28,867

Solution 1

Scripts, historically, blocked additional resources from being downloaded more quickly. By placing them at the bottom, your style, content, and media could download more quickly giving the perception of improved performance.

Further reading: The async and defer attributes.

Solution 2

In my opinion, this is an outdated practice. More recently, the preference is for JavaScript to separate any code that requires the DOM to be present into a "DOMContentLoaded" event listener. This isn't necessarily all logic; lots of code can initialize without access to the complete DOM.

It's true that this causes a small moment when only the script file is being retrieved, and nothing else (for instance, images). This small window can be skipped by adding the async attribute, but even without it I recommend putting script tags in the head so that the browser knows as soon as possible to load them, rather than saving them (and any future JS-initiated requests) for last.

Solution 3

It is a best practice to put JavaScript tags just before the closing tag rather than in the 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. If we put our JavaScript links in the head section, the entire JavaScript file will load before loading any of the HTML, which could cause a few problems.

1.If you have code in your JavaScript that alters HTML as soon as the JavaScript file loads, there won't actually be any HTML elements available for it to affect yet, so it will seem as though the JavaScript code isn't working, and you may get errors. 2.If you have a lot of JavaScript, it can visibly slow the loading of your page because it loads all of the JavaScript before it loads any of the HTML. When you place your JavaScript links at the bottom of your HTML body, it gives the HTML time to load before any of the JavaScript loads, which can prevent errors, and speed up website response time.

One more thing: While it is best to include your Javascript at the end of your HTML , putting your Javascript in the of your HTML doesn't ALWAYS cause errors. When using jQuery, it is common to put all of your code inside a "document ready" function:

$("document").ready(function(){ // your code here });

This function basically says, don't run any of the code inside until the document is ready, or fully loaded. This will prevent any errors, but it can still slow down the loading time of your HTML, which is why it is still best to include the script after all of the HTML.

Solution 4

Images placed below the script tag will wait to load until the JS script loads. By placing the script tag at the bottom you load images first, giving the appearance of a faster page load.

Solution 5

I think it depends on your website or app. Some web apps are based on JavaScript. Then it does not make sense to include it at the bottom of the page, but load it immediately. If JavaScript just adds some not so important features to some content based page, then better load it at the end. Loading time will almost be the same, but the user will see the important parts earlier (before the page finished loading).

It’s not about a whole site loading faster, but giving a user the impression of some website loading faster.

For example: This is why Ajax based websites can give a much faster impression. The interface is always the same. Just some content parts will alter.

Share:
28,867

Related videos on Youtube

Artem Svirskyi
Author by

Artem Svirskyi

Updated on July 25, 2022

Comments

  • Artem Svirskyi
    Artem Svirskyi almost 2 years

    I know this question was asked many times, but I haven't found answer. So why its recommended to include scripts at the end of body tag for better rendering?

    From Udacity course https://www.udacity.com/course/ud884 - rendering starts after DOM and CSSOM are ready. JS is HTML parse blocking and any script starts after CSSOM is ready.

    So if we got:

    <html>
        <head>
            <meta name="viewport" content="width=device-width,initial-scale=1">
            <title>CRP</title>
            <link rel="stylesheet" href="styles.css">
        </head>
        <body>
            <!-- content -->
            <script src="script.js"></script>
        </body>
    </html>
    

    CRP would be:

    CSSOM ready > JS execute > DOM ready > Rendering
    

    And if script is at head:

    <html>
        <head>
            <meta name="viewport" content="width=device-width,initial-scale=1">
            <title>CRP</title>
            <link rel="stylesheet" href="styles.css">
            <script src="script.js"></script>
        </head>
        <body>
            <!-- content -->
        </body>
    </html>
    

    CRP would be the same:

    CSSOM ready > JS execute > DOM ready > Rendering
    

    This question is only about "sync" scripts (without async/defer attribute).

    • epascarello
      epascarello almost 9 years
    • ernesto
      ernesto over 8 years
      Rendering is not done at once, but incrementally. If a JS is blocking at the end of the body, the page up to that point will be rendered (if CSSOM is ready).
  • Chris Walter
    Chris Walter almost 9 years
    I noticed you said historically. Is that still true, or do newer browsers work around this?
  • Sampson
    Sampson almost 9 years
    @ChrisWalter The number of connections to the server in the past were more limited, and with the dawn of HTTP2 we can get all of the data down much faster. Additionally, scripts can have their execution deferred these days as well.
  • Roko C. Buljan
    Roko C. Buljan almost 9 years
    Yes, but it depends on the number of images. Since browsers handle src simultaneously till some number of requests. Also note that you can always use async property for the <script> tag.
  • Chris Walter
    Chris Walter almost 9 years
    So you are referring to adding defer to the end of your script tag as seen here: w3schools.com/tags/att_script_defer.asp
  • Roko C. Buljan
    Roko C. Buljan almost 9 years
    Nice catch that actually not all JS does brutal stuff to the DOM object.
  • Brian
    Brian almost 9 years
    The HTTP/1.1 specification suggests that browsers download no more than two components in parallel per hostname. @RokoC.Buljan
  • Sampson
    Sampson almost 9 years
    @ChrisWalter You should look into both the async and defer attributes, and preferably not via w3schools.
  • Chris Walter
    Chris Walter almost 9 years
    W3Schools was my first hit on Google and seemed to get the point across :) I'd add to your answer that those attributes are not supported until Internet Explorer 10, so it'd still be worth adding your JavaScript to the end of your HTML.
  • Sampson
    Sampson almost 9 years
    @ChrisWalter Internet Explorer 4 supported defer. Its implementation was revised in version 10.
  • Chris Walter
    Chris Walter almost 9 years
  • Chris Walter
    Chris Walter almost 9 years
    I stand corrected. Easy to misinterpret things on those available in version sites.
  • Vaquita
    Vaquita about 5 years
    The links given in the answer is not working. Please update. @Sampson