🚀Introducing Bright Star: AI-Powered, Autonomous Security Testing & Remediation! Learn more>>

Back to blog
Published: Jun 2nd, 2021 /Modified: Mar 25th, 2025

How DOM Based XSS Attacks work

Time to read: 7 min

What is DOM Based XSS?

According to various research and studies, up to 50% of websites are vulnerable to DOM Based XSS vulnerabilities. Security researchers detected DOM XSS issues in high profile internet companies like Google, Yahoo, and Amazon.

The Document Object Model is a programming interface that gives developers the ability to access the document (web page) and manipulate it by executing operations, therefore this interface defines the structure of documents by connecting the scripting language to the actual webpage.

DOM-based XSS, also known as Type-0 XSS, is an XSS attack in which the attack payload is executed by altering the DOM in the victim’s browser. This causes the client to run code, without the user’s knowledge or consent. The page itself (i.e. the HTTP response) will not change, but a malicious change in the DOM environment will cause the client code contained in the page to execute in a different way.

This differs from reflected or stored XSS attacks, which place the attack payload into the response page due to server-side vulnerabilities. DOM XSS is a vulnerability on the client side.

In this article, you will learn:

DOM XSS Example #1: Vulnerable Content

As an example the following HTML page (vulnerable.site/welcome.html) contains this content:

<HTML>
<TITLE>Welcome!</TITLE>
Hi
<SCRIPT>
var pos=document.URL.indexOf("name=")+5;
document.write(document.URL.substring(pos,document.URL.length));
</SCRIPT>
<BR>
Welcome
…
</HTML>

Normally, this HTML page would be used for welcoming the user, e.g.:

http://www.vulnerable.site/welcome.html?name=Joe

However, a request such as the one below would result in an XSS condition:

http://www.vulnerable.site/welcome.html?name=alert(document.cookie)

DOM XSS Example #2: Vulnerable User Form

Let’s say we have a code that creates a form. This form lets a user select a timezone. The query string also has a default timezone. It’s defined by the defaulttimezone parameter. The code would look something like this:

Select your Time Zone:

<select><script>

document.write("<OPTION value=1>"+document.location.href.substring(document.location.href.indexOf("default=")+8)+"</OPTION>");
document.write("<OPTION value=2>CET</OPTION>");

</script></select>

The http://www.some.site/page.html?default=CST URL then invokes the page. Hackers can now send a URL that looks like this:

http://www.example.site/page.html?default=<script>alert(document.cookie)</script>

to launch a DOM-based XSS attack. When an unsuspecting user clicks this link the browser sends a request to www.example.site for:
/page.html?default=<script>alert(document.cookie)</script> 

The server responds with a page that contains the malicious Javascript code. The browser now creates a DOM object for that page and the document.location object will contain this string:

http://www.example.site/page.html?default=<script>alert(document.cookie)</script>

Where is the problem?

The original Javascript code on this page won’t expect the default parameter to have any HTML markup. Because of this, it will echo it into the DOM during runtime. Any browser will render the resulting page and end up executing the malicious script:(alert(document.cookie))

Keep in mind that the server’s HTTP response won’t contain the attacker’s payload. The DOM XSS payload will reveal itself in the client-side script at runtime. It happens when the flawed script opens the DOM variable (document.location) while assuming that it isn’t malicious.

How Do DOM XSS Attacks Work?

DOM XSS attacks typically follow this process:

  1. The victim’s browser receives a link, sends an HTTP request to www.vulnerable.site, and receives a static HTML page.
  2. The victim’s browser then starts parsing this HTML into DOM. The DOM contains an object called document, which contains a property called URL, and this property is populated with the URL of the current page, as part of DOM creation.
  3. When the parser processes the Javascript code, it executes it and it modifies the raw HTML of the page. In this case, the code references document.URL, and so, a part of this string is embedded at parsing time in the HTML.
  4. The string is then parsed and the Javascript code is executed in the context of the same page, resulting in XSS.

The logic behind DOM XSS is that an input from the user – source – goes to an execution point – sink. In the previous examples, our source was document.write and the sink was alert(document.cookie)

After the malicious code is executed by the website, attackers can steal the cookies from the user’s browser or change the behavior of the page on the web application.

How Do Attackers Exploit DOM XSS Vulnerabilities?

Let’s dive a bit deeper to understand the possible sources, or entry points, attackers can use to perform DOM XSS attacks, and the “sinks” or DOM objects in which they can execute malicious code.

Source

A source is a JavaScript property that contains data that an attacker could potentially control:

document.URL
document.referrer
location
location.href
location.search
location.hash
location.pathname

Sink

A sink is a DOM object or function that allows JavaScript code execution or HTML rendering.

eval
setTimeout
setInterval
document.write
element.innerHTML

Any application is vulnerable to DOM-based cross-site scripting if there is an executable path via which data can develop from source to sink.

Different sources and sinks have various properties and behaviors that can impact exploitability, and determine what methods are used. Additionally, the application’s scripts might execute validation or other processing of data that must be accommodated when aiming to exploit a vulnerability.

In reality, the attacker would encode the URL payload so the script is not visible. Some browsers, for example, Mozzila may automatically encode the < and > characters in the document.URL when the URL is not directly typed in the address bar, and therefore it is not vulnerable to the attack shown in the example above. 

Embedding a script directly in the HTML is just one attack access point, other scenarios do not require these characters, nor embedding the code into the URL directly. Therefore, browsers in general are not entirely immune to DOM XSS either.

How DOM based XSS attacks work

What is the Difference Between Standard XSS and DOM-Based XSS?

Let’s review the key differences between classic reflected or stored XSS and DOM-based XSS.

Root Cause 

The root of both the classic XSS and a DOM-based vulnerability is a vulnerability in the source code.

Premises

  • For classic XSS, the premise is the malicious embedding of client-side data by the server in the outbound HTML pages. 
  • For DOM-based XSS, it’s the malicious referencing and use of DOM objects in the client-side.

The Page Type

  • Classic XSS attacks target dynamic page types. 
  • DOM-based XSS attacks can target both static and dynamic page types.

What Can Detect Them

Logs and intrusion detection systems can detect classic XSS attacks. DOM-based XSS can remain unnoticed server-side if the hacker uses evading techniques.

How to Identify Vulnerabilities

For both classic and DOM-based XSS attacks you use vulnerability detection tools that can perform automatic penetration testing. The code also needs to be reviewed. The only difference is that for classic XSS you do it server-side, while for DOM XSS you do it client-side.

DOM XSS Attacks Prevention

You cannot detect DOM XSS attacks from the server-side. The malicious payload doesn’t even reach the server in most cases. Due to this, it can’t be sanitized in the server-side code. The root of the issue is in client-side code, the code of the page. 

You’re free to utilize any prevention techniques for DOM XSS that you can use for standard XSS attacks. There’s only one thing you need to pay attention to. For DOM XSS attacks you need to review and sanitize the client-side code instead of the server-side code.

There are three main ways to defend against DOM XSS:

  1. Don’t use client data for sensitive actions – refrain from using data that was received from the client for any kind of sensitive actions on the client side, like redirection or rewriting.
  2. Sanitize client-side code – do this by inspecting references to DOM objects, especially those that pose a threat like referrer, URL, location, and so on. This is important in cases where the DOM can be modified.
  3. Use Content Security Policy (CSP) – this is a Mozilla capability which is specially designed to prevent XSS and similar attacks. CSP restricts the domains from which the browser will accept scripts for execution. Scripts originating from other domains will not be executed.
  4. Automated detection of DOM XSS vulnerabilities – you can use Bright, an AI-powered application security testing solution that can identify DOM XSS vulnerabilities with zero false positives. Scan your web applications regularly to detect new vulnerabilities and resolve them. Learn more about Bright

Subscribe to Bright newsletter!