Skip to content
Laviyx Learn

Try

HTML course menu

HTML Validation and Best Practices: Writing Clean, Valid HTML

Check your pages with the W3C Nu HTML Checker, fix the most common validation errors, and follow HTML best practices for structure, naming, formatting, performance, accessibility and maintainability.

Advanced6 min readUpdated
On this page

Browsers display almost anything, even badly broken HTML. That is convenient, but it hides mistakes that can break layouts in another browser, confuse screen readers, or make JavaScript behave strangely. Validating your HTML and following a few habits catches these early.

Validating HTML#

The W3C Nu HTML Checker (validator.w3.org/nu) checks a page against the HTML standard. You can:

  • enter the URL of a published page;
  • upload a file; or
  • paste HTML directly with "Text input".

It lists errors (invalid HTML) and warnings (allowed, but probably not what you meant), each with a line number. Many code editors can also show problems as you type through extensions.

The most common errors#

ErrorExampleFix
Missing alt on an image<img src="a.png">Add meaningful alt text, or alt="" if decorative
Duplicate idTwo elements with id="card"Make ids unique; use a class for groups
Unclosed or overlapping elements<b><i>text</b></i>Close in reverse order
Block element inside <p><p><div>...</div></p>Close the paragraph first, or use a <div> instead
Elements in the wrong parentText directly inside <ul>Only <li> goes directly inside lists
Missing <title> or langAdd them to every page
Unescaped & in URLshref="?a=1&b=2"Usually tolerated, but &amp; is the strict form inside HTML
Obsolete elements and attributes<center>, <font>, bgcolorUse CSS
Label for pointing nowhere<label for="mail"> with no id="mail"Match the ids exactly

Best practices#

Structure and meaning#

  • Start with <!DOCTYPE html>, <html lang>, <meta charset="utf-8">, the viewport meta tag and a unique <title>.
  • Choose elements by meaning; use <div> and <span> only when nothing else fits.
  • Use one <h1>, then headings in order.
  • Use <header>, <nav>, <main> and <footer> landmarks.

Keep concerns separate#

  • Content and structure in HTML, presentation in CSS files, behaviour in JavaScript files.
  • Avoid inline style attributes and inline onclick handlers in real projects; they are hard to reuse and maintain.
  • Never use tables or <br> tags for layout.

Formatting and naming#

  • Write tags and attributes in lowercase and always quote attribute values.
  • Indent nested elements consistently. A formatter such as Prettier can do it automatically.
  • Name classes after what things are (product-card), not how they look (blue-box).
  • Use lowercase, hyphenated file names without spaces: about-us.html, team-photo.jpg.

Accessibility#

  • Alt text for images, labels for every field, real buttons and links.
  • Visible focus styles, sufficient colour contrast, captions for video.
  • Test with the keyboard. See Accessibility.

Performance#

  • Set width and height on images and use modern formats and srcset.
  • Lazy-load images and iframes below the first screen.
  • Load scripts with defer, async or type="module".
  • Do not load what you do not use.

Security and privacy#

  • Never put passwords, keys or personal data in HTML, comments or data-* attributes; anyone can view the source.
  • Validate form data on the server, not just in the browser.
  • Use sandbox on iframes with third-party content.

A final checklist#

Before you publish a page, check that:

  1. The validator reports no errors.
  2. The page has a meaningful title and description.
  3. Headings form a logical outline.
  4. Every image has suitable alt text, and every field a label.
  5. Everything works with the keyboard alone.
  6. The page works on a phone screen and when zoomed to 200%.
  7. Links all work.

Practice#

Practice exercise

Find the problems in this page, then rewrite it as valid, well-structured HTML:

HTML
<html>
<title>my page</title>
<body>
<center><font size="6">Welcome</font></center>
<p>Our products:
<ul><li>Pens<li>Notebooks</ul>
</p>
<img src="shop photo.jpg">
<div id="info">Open daily</div><div id="info">Call us</div>
</body>
</html>
Show solution
HTML
<!DOCTYPE html>
<html lang="en">
  <head>
    <meta charset="utf-8">
    <meta name="viewport" content="width=device-width, initial-scale=1">
    <title>Stationery Shop | Pens and Notebooks</title>
    <style>h1 { text-align: center; }</style>
  </head>
  <body>
    <h1>Welcome</h1>
    <p>Our products:</p>
    <ul>
      <li>Pens</li>
      <li>Notebooks</li>
    </ul>
    <img src="shop-photo.jpg" alt="The front of our shop on Main Road" width="400" height="300">
    <p class="info">Open daily</p>
    <p class="info">Call us</p>
  </body>
</html>
Result

Fixes: added the DOCTYPE, lang, <head>, charset, viewport and a descriptive title; replaced the obsolete <center> and <font> with a heading and CSS; moved the list out of the paragraph and closed the list items; renamed the image without a space and added alt text and size; changed the duplicate ids to a class. (The image file does not exist here, so the preview shows its alt text.)

Key takeaway#

Finished this lesson?