[html] In HTML5, can the <header> and <footer> tags appear outside of the <body> tag?

I'm currently using the above tags in this way (classic tag order):

<html>
  <head>...</head>
  <body>
    <header>...</header>
    <section>...</section>
    <footer>...</footer>
  </body>
</html>

Tag usage and specifications were very rigid in previous versions of HTML (4.x), while HTML5 doesn't really need <head> and even <body> tags.

So I would use the following structure, which IMHO is much more semantic than the previous one.

<html>
  <header>...</header>     <!-- put header and footer outside the body tag -->
  <body>
    <section>...</section>
    <section>...</section>
    <section>...</section>
  </body>
  <footer>...</footer>
</html>

What do you think?

This question is related to html tags

The answer is


Well, the <head> tag has nothing to do with the <header> tag. In the head comes all the metadata and stuff, while the header is just a layout component.
And layout comes into body. So I disagree with you.


According to the HTML standard, the content model of the HTML element is:

A head element followed by a body element.

You can either define the BODY element in the source code:

<html>
    <body>
        ... web-page ...
    </body>
</html>

or you can omit the BODY element:

<html>
    ... web-page ...
</html>

However, it is invalid to place the BODY element inside the web-page content (in-between other elements or text content), like so:

<html>
    ... content ...
    <body>
        ... content ...
    </body>
    ... content ...
</html>

I agree with some of the others' answers. The <head> and <header> tags have two unique and very unrelated functions. The <header> tag, if I'm not mistaken, was introduced in HTML5 and was created for increased accessibility, namely for screen readers. It's generally used to indicate the heading of your document and, in order to work appropriately and effectively, should be placed inside the <body> tag. The <head> tag, since it's origin, is used for SEO in that it constructs all of the necessary meta data and such. A valid HTML structure for your page with both tags included would be like something like this:

<!DOCTYPE html/>
<html lang="es">
    <head>
        <!--crazy meta stuff here-->
    </head>
    <body>
        <header>
            <!--Optional nav tag-->
            <nav>
            </nav>
        </header>
        <!--Body content-->
    </body>
</html>

If you really want it to look more semantic like having the <body> in the middle you can use the <main> element. With all the recent advances the <body>element is not as semantic as it once was but you just have to think of it as a wrapper in which the view port sees.

<html>
    <head>
    </head>
    <body>
        <header>
        </header>
        <main>
            <section></section>
            <article></article>
        </main>
        <footer>
        </footer>
    <body>
</html>

Let's get a canonical answer here. I will reference the HTML5 spec.

First of all, 12.1.2.4 Optional tags:

A head element's start tag may be omitted if the element is empty, or if the first thing inside the head element is an element.

A head element's end tag may be omitted if the head element is not immediately followed by a space character or a comment.

A body element's start tag may be omitted if the element is empty, or if the first thing inside the body element is not a space character or a comment, except if the first thing inside the body element is a script or style element.

A body element's end tag may be omitted if the body element is not immediately followed by a comment.

Then, the 4.1.1 The html element:

Content model: A head element followed by a body element.

Having the cited restrictions and strictly defined element order, we can easily work out what are the rules for placing implicit <body> tag.

Since <head/> must come first, and it can contain elements only (and not direct text), all elements suitable for <head/> will become the part of implicit <head/>, up to the first stray text or <body/>-specific element. At that moment, all remaining elements and text nodes will be placed in <body/>.


Now let's consider your second snippet:

<html>
  <header>...</header>
  <body>
    <section>...</section>
    <section>...</section>
    <section>...</section>
  </body>
  <footer>...</footer>
</html>

Here, the <header/> element is not suitable for <head/> (it's flow content), the <body> tag will be placed immediately before it. In other words, the document will be understood by browser as following:

<html>
  <head/>
  <body>
    <header>...</header>
    <body>
      <section>...</section>
      <section>...</section>
      <section>...</section>
    </body>
    <footer>...</footer>
  </body>
</html>

And that's certainly not what you were expecting. And as a note, it is invalid as well; see 4.4.1 The body element:

Contexts in which this element can be used: As the second element in an html element.

[...]

In conforming documents, there is only one body element.


Thus, the <header/> or <footer/> will be correctly used in this context. Well, they will be practically equivalent to the first snippet. But this will cause an additional <body/> element in middle of a <body/> which is invalid.


As a side note, you're probably confusing <body/> here with the main part of the content which has no specific element. You could look up that page for other solutions on getting what you want.

Quoting 4.4.1 The body element once again:

The body element represents the main content of the document.

which means all the content. And both header and footer are part of this content.


Even though the <head> and <body> tags aren't required, the elements are still there - it's just that the browser can work out where the tags would have been from the rest of the document.

The other elements you're using still have to be inside the <body>


I see what you are trying to do, you are trying to use the <body> tag as the container for the main content of the page. Instead, use the <main> tag, as specified in the HTML5 spec. I use this layout:

    <!DOCTYPE html>
    <html>
        <head> *Metadata* </head>
        <body>
            <header>
                *<h1> and other important stuff </h1>*
                <nav> *Usually a formatted <Ul>* </nav>
            </header>
            <main> *All my content* </main>
            <footer> *Copyright, links, social media etc* </footer>
        </body>
    </html>

I'm not 100% sure but I think that anything outside the <body> tag is considered metadata and will not be rendered by the browser. I don't think that the DOM can access it either.

To conclude, use the <main> tag for your content and keep formatting your HTML the correct way as you have in your first code snippet. You used the <section> tag but I think that comes with some weird formatting issues when you try to apply CSS.


This is the general structure of an html document.

<html>
    <head>
        Title, meta-data, scripts, etc go here... Don't confuse with header
    </head>
    <body>
        You body stuff comes here...
        <footer>
            Your footer stuff goes here...
        </footer>
    </body>
</html>