Reference · Quick lookup
The iframe
cheat sheet.
Everything that matters about the <iframe> element — every attribute, every sandbox flag, every Permissions-Policy feature, every defense header you can send. One page. Paste-ready snippets at the bottom.
Every iframe attribute
| Attribute | Value | What it does |
|---|---|---|
src | URL | URL of the document to embed. Mutually exclusive with srcdoc. |
srcdoc | HTML string | Inline HTML to render. Overrides src when both are present. |
name | token | Targetable name for window.open() and form target=… |
title | string | Accessible label. Required for screen-reader compliance. |
sandbox | tokens | Capability deny-list. See the dedicated sandbox section below. |
allow | Permissions-Policy | Feature allowlist (camera, geolocation, payment, etc.). See section below. |
allowfullscreen | boolean | Lets the frame call requestFullscreen(). Equivalent to allow="fullscreen". |
referrerpolicy | policy | Referer header sent on the request. See section below. |
loading | lazy / eager | Defer off-screen frames until they near the viewport. |
fetchpriority | high / low / auto | Hint to the browser about resource scheduling. |
width / height | px or % | Dimensions of the rendered frame. |
csp | policy | Experimental — embed-only CSP enforced on the frame. Limited support. |
Every sandbox flag
Space-separated tokens in the sandbox attribute. Empty value strips everything; each allow-* re-enables one capability. See the dedicated sandbox guide for caveats and recipes.
| Flag | Re-enables |
|---|---|
| (empty) | Maximum restriction: no scripts, no forms, no popups, opaque origin. |
allow-scripts | Re-enable JavaScript. |
allow-same-origin | Restore the real origin (dangerous with allow-scripts on a same-origin frame). |
allow-forms | Re-enable form submission. |
allow-popups | Re-enable window.open(). |
allow-popups-to-escape-sandbox | Popups created by the frame are unsandboxed. |
allow-modals | Re-enable alert / confirm / prompt / print. |
allow-top-navigation | Re-enable writes to window.top.location. |
allow-top-navigation-by-user-activation | Top-navigation, but only after a click/keypress. |
allow-downloads | Re-enable download triggers. |
allow-presentation | Re-enable the Presentation API. |
allow-pointer-lock | Re-enable requestPointerLock(). |
allow-orientation-lock | Re-enable screen.orientation.lock(). |
allow-storage-access-by-user-activation | Frame can call requestStorageAccess() for same-site cookies. |
Permissions-Policy features for the allow attribute
Space-separated or semicolon-separated list. Empty parens () = block completely; (self) = allow same-origin only; (self "https://x.example") = allow self + specific origins; * = allow everywhere.
| Feature token | What it controls |
|---|---|
camera | MediaDevices.getUserMedia({ video: true }) |
microphone | MediaDevices.getUserMedia({ audio: true }) |
geolocation | Navigator.geolocation API |
payment | Payment Request API. Required for Apple Pay / Google Pay inside frames. |
fullscreen | Element.requestFullscreen() |
autoplay | Audio/video autoplay |
encrypted-media | EME (DRM-protected media) |
clipboard-read / clipboard-write | Async Clipboard API |
publickey-credentials-get | WebAuthn assertion (passkey sign-in) |
usb | WebUSB |
serial | Web Serial API |
hid | WebHID |
midi | Web MIDI |
xr-spatial-tracking | WebXR (VR/AR) |
display-capture | getDisplayMedia (screen capture) |
cross-origin-isolated | Required for SharedArrayBuffer / high-resolution timers |
interest-cohort / browsing-topics | FLoC and Topics API. Set to () to opt out. |
referrerpolicy values
| Policy | What gets sent in the Referer header |
|---|---|
no-referrer | Never send the Referer header. |
no-referrer-when-downgrade | Send full URL on same- or higher-security navigations; omit on HTTPS→HTTP. |
origin | Send only the origin (scheme + host + port). |
origin-when-cross-origin | Full URL same-origin, origin-only cross-origin. |
same-origin | Full URL same-origin, nothing cross-origin. |
strict-origin | Send origin only, never on HTTPS→HTTP. |
strict-origin-when-cross-origin | Default in modern browsers. Full URL same-origin, origin-only cross-origin, nothing on HTTPS→HTTP. |
unsafe-url | Always send full URL. Avoid — leaks path data cross-origin. |
loading and fetchpriority
loading="lazy"— defer the frame until it nears the viewport. See the dedicated lazy-loading guide.loading="eager"— load immediately (default).fetchpriority="high"— hint to the browser this frame is critical (rarely needed for iframes).fetchpriority="low"— deprioritise. Useful for tracking and analytics iframes.
Defense headers for the embedding page
Headers you send on responses you want to protect. See the dedicated clickjacking guide for context.
| Header | What it does |
|---|---|
X-Frame-Options: DENY | Block any iframe from embedding this page. Legacy header, still respected. |
X-Frame-Options: SAMEORIGIN | Only same-origin pages may embed. Riskier than DENY because of subdomains. |
Content-Security-Policy: frame-ancestors 'none' | CSP-level equivalent of X-Frame-Options DENY. Supersedes XFO where supported. |
Content-Security-Policy: frame-ancestors 'self' https://partner.example | Allow specific partner origins to embed. CSP-only — XFO cannot do allowlists. |
Content-Security-Policy: frame-src 'self' https://*.youtube.com | Limits which origins the page itself is allowed to load iframes FROM. |
Cross-Origin-Embedder-Policy: require-corp | Required (with COOP) for SharedArrayBuffer. Affects all subresources, including iframes. |
Cross-Origin-Opener-Policy: same-origin | Isolates the browsing context group. Pairs with COEP. |
Permissions-Policy: camera=() | Header-level equivalent of the allow attribute. Applies to the page and all its iframes. |
Snippets you will paste
Strict, no-trust embed of user HTML
<iframe sandbox srcdoc="<h1>Untrusted</h1>"></iframe>YouTube embed with full defenses
<iframe
src="https://www.youtube-nocookie.com/embed/VIDEO_ID"
title="Video title"
loading="lazy"
referrerpolicy="strict-origin-when-cross-origin"
allow="autoplay; encrypted-media; picture-in-picture"
allowfullscreen
></iframe>Stripe payment frame
<iframe
src="https://js.stripe.com/v3/elements-..."
allow="payment"
sandbox="allow-scripts allow-same-origin allow-forms allow-popups"
></iframe>Maximum framing defense on a sensitive page
X-Frame-Options: DENY
Content-Security-Policy: frame-ancestors 'none'
Permissions-Policy: camera=(), microphone=(), geolocation=(), interest-cohort=()List every iframe on the current page
document.querySelectorAll('iframe')Check whether the current page is itself framed
const framed = window.self !== window.top;Find iframes that are hidden / 1×1 pixels
Array.from(document.querySelectorAll('iframe')).filter(f =>
f.offsetParent === null || f.offsetWidth <= 1 || f.offsetHeight <= 1
);