How to Use Async and Defer in Script Tag in HTML
Use the
async attribute in a <script> tag to load the script asynchronously without blocking HTML parsing, executing it as soon as it loads. Use defer to load the script asynchronously but delay execution until after the HTML document is fully parsed.Syntax
The <script> tag can include async or defer attributes to control how the browser loads and runs JavaScript files.
async: Loads the script asynchronously and executes it immediately when ready, without waiting for HTML parsing to finish.defer: Loads the script asynchronously but waits to execute it until after the entire HTML document is parsed.- Both attributes only work with external scripts using the
srcattribute.
html
<script src="script.js" async></script> <script src="script.js" defer></script>
Example
This example shows two scripts: one with async and one with defer. Notice how the async script runs as soon as it loads, while the defer script waits until the page is fully parsed.
html
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <meta name="viewport" content="width=device-width, initial-scale=1.0"> <title>Async vs Defer Example</title> <script src="async-script.js" async></script> <script src="defer-script.js" defer></script> </head> <body> <h1>Check the console to see script execution order</h1> </body> </html>
Output
Page shows heading 'Check the console to see script execution order'. In browser console, 'Async script loaded' logs as soon as async-script.js loads, possibly before HTML parsing finishes. 'Defer script loaded' logs after the whole HTML is parsed.
Common Pitfalls
- Using
asyncordeferon inline scripts or scripts withoutsrchas no effect. asyncscripts run as soon as they load, which can cause unpredictable execution order if multiple async scripts depend on each other.deferscripts always execute in the order they appear in the HTML, which is safer for dependent scripts.- Not using either attribute blocks HTML parsing until the script loads and runs, slowing page rendering.
html
<!-- Wrong: async on inline script does nothing --> <script async>console.log('Inline script');</script> <!-- Right: async on external script --> <script src="file.js" async></script>
Quick Reference
| Attribute | When Script Loads | When Script Executes | Execution Order | Use Case |
|---|---|---|---|---|
| async | Asynchronously (does not block HTML parsing) | Immediately after loading | Unpredictable if multiple async scripts | Independent scripts that don't rely on others |
| defer | Asynchronously (does not block HTML parsing) | After HTML parsing completes | In order of appearance | Scripts that depend on DOM or each other |
| (none) | Synchronously (blocks HTML parsing) | Immediately before HTML parsing completes | In order of appearance | Legacy or critical scripts that must run before page renders |
Key Takeaways
Use
async to load scripts without blocking but expect unpredictable execution order.Use
defer to load scripts without blocking and run them after HTML parsing in order.Both
async and defer only work with external scripts using src.Avoid blocking page rendering by not using scripts without async or defer unless necessary.
Choose
defer for scripts that depend on the DOM or other scripts.