What Is DOM-Based XSS?

On this page
  1. Sources and sinks
  2. Why does it evade server defenses?
  3. How do you prevent DOM XSS?

DOM-based XSS is a form of cross-site scripting where the entire vulnerable data flow lives in the browser. Client-side JavaScript reads attacker-influenced input and writes it into a dangerous sink that executes it — often without the payload ever reaching the server. That makes it invisible to server-side defenses and a favorite in modern single-page apps.

Sources and sinks#

DOM XSS is best understood as data flowing from a source to a sink:

Sources (input)Sinks (execution)
location.hash, location.searchinnerHTML, outerHTML
document.URL, document.referrerdocument.write
postMessage dataeval, Function
localStorage valuessetAttribute on src/href

The bug is any path where untrusted source data reaches a sink without safe handling. A classic one-liner: reading location.hash and assigning it to element.innerHTML.

Why does it evade server defenses?#

Because the server may never see the payload. Data after the # in a URL is not even sent to the server; postMessage and localStorage are purely client-side. A perfectly filtered backend and a strict server-side CSP can still sit atop a page that XSSes itself in JavaScript.

How do you prevent DOM XSS?#

  • Avoid dangerous sinks — prefer textContent over innerHTML; never eval untrusted data.
  • Use safe APIs — framework binding that escapes by default; Trusted Types to lock down sinks.
  • Validate the source — treat hash, postMessage, and storage as hostile input.

DOM XSS is the client-side sibling of reflected and stored XSS. More at the Web Security hub.

Frequently asked questions#

What is DOM-based XSS?

DOM-based XSS is a cross-site scripting flaw where the vulnerable data flow happens entirely in the browser: client-side JavaScript takes attacker-controllable input (a source like location.hash) and writes it into a dangerous sink (like innerHTML) that executes it. The server may never see the payload, so server-side filtering misses it.

What are sources and sinks in DOM XSS?

A source is where untrusted data enters the page — location.hash, document.URL, referrer, postMessage. A sink is a function that can turn data into code or markup — innerHTML, document.write, eval, setAttribute on certain attributes. DOM XSS occurs when data flows from a source to a sink without safe handling.

Sources & further reading