Link styles and scripts to your HTML page — inline CSS, internal style blocks, external stylesheets, and script tags with defer and async explained.
Why avoid it: inline styles have the highest CSS specificity, making them nearly impossible to override without !important. When it is acceptable: dynamic values set by JavaScript (e.g. element.style.width), or generated content where adding a class is not practical.
<!-- Applied directly on the element — highest specificity -->
<p style="color: crimson; font-weight: bold;">
Important notice.
</p>
<div style="display: flex; align-items: center; gap: 1rem; padding: 1rem;">
<img src="icon.svg" alt="" style="width: 24px;" />
<span>Status: Online</span>
</div>When: single-page sites, email templates, or page-specific overrides. Why not always: styles inside a <style> block are re-downloaded with every page — they cannot be cached separately the way an external .css file can.
<!DOCTYPE html>
<html lang="en">
<head>
<style>
body {
font-family: sans-serif;
margin: 0;
}
h1 {
color: navy;
}
.card {
border: 1px solid #ddd;
border-radius: 8px;
padding: 1rem;
}
</style>
</head>
<body>
<h1>Hello</h1>
<div class="card">Card content</div>
</body>
</html>Why: the browser caches the file after the first visit — every subsequent page reuses it instead of downloading styles again. Where: in <head>, so styles are applied before the body renders and the user never sees unstyled content.
rel required — Relationship to the linked resource. Always "stylesheet" for CSS files.href required — Path to the CSS file.media — Media condition that controls when the stylesheet applies — e.g. "print" or "(max-width: 768px)".type — MIME type of the resource. Defaults to "text/css" and can be omitted.<!-- In your HTML <head> -->
<head>
<link rel="stylesheet" href="styles.css" />
</head>
<!-- styles.css (separate file) -->
<!--
body { margin: 0; font-family: sans-serif; }
h1 { color: navy; }
.btn { padding: 8px 16px; background: teal; color: white; }
-->Why defer: a <script> in <head> without defer pauses HTML parsing until the script downloads and executes — the user sees a blank page. defer downloads in parallel and runs after parsing. When async: only for fully independent scripts like analytics that do not depend on the DOM or other scripts.
src — URL of an external JavaScript file. When present, the element must not have inline content.defer — Boolean. Downloads in parallel with HTML parsing and runs after parsing is complete, in document order. Best default for most scripts.async — Boolean. Downloads in parallel and runs as soon as ready — order is not guaranteed. Only use for fully independent scripts (e.g. analytics).type — "module" treats the script as an ES module (enables import/export). Omit for classic scripts.nomodule — Boolean. Script runs only in browsers that do not support ES modules — used as a fallback.<!-- Inline script -->
<script>
console.log('Hello from inline script')
</script>
<!-- External script placed before </body> -->
<script src="app.js"></script>
<!-- defer — downloads in parallel, runs after HTML is parsed -->
<head>
<script src="app.js" defer></script>
</head>
<!-- async — downloads in parallel, runs immediately when ready -->
<!-- Order is NOT guaranteed — only use for independent scripts -->
<head>
<script src="analytics.js" async></script>
</head>