What is Open Redirect Vulnerability? #
An open redirect occurs when a web application redirects a user to an external URL without properly validating or controlling the destination. This vulnerability allows attackers to trick users into navigating to malicious sites, often for purposes like phishing or spreading malware.
Two main types of open redirects #
There are two main types of open redirects, each with distinct characteristics and potential security risks: server-side open redirects and DOM-based (client-side) open redirects.
Server-Side Open Redirects #
In server-side open redirects, a web server processes the request and redirects the user to an external URL. The server uses URL parameters or other user inputs to determine the redirect target. If the server fails to validate or sanitize the input, attackers can manipulate the redirect to send users to malicious websites.
DOM-based (Client-Side) Open Redirects #
DOM-based open redirects occur on the client-side, within the browser, via JavaScript or other client-side code. In this type of open redirect, the redirection logic happens in the browser itself, and the vulnerability arises when the client-side code (such as JavaScript) does not properly handle user input before performing the redirect.
In this blog, we will focus specifically on the DOM-based redirect vulnerability.
What is DOM? #
The Document Object Model (DOM) is a programming interface that represents the structure of a web page. It allows developers to interact with and manipulate the content of a webpage using programming languages like JavaScript. The DOM treats each part of a page—such as elements, attributes, and text—as objects, which can be accessed and modified.
When a webpage is loaded, the browser creates the DOM, providing a dynamic representation of the page. This enables real-time updates to the page without needing to reload it.
Example of DOM #
Here’s a simple example where JavaScript uses the DOM to change the content of a webpage:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>DOM Example</title>
</head>
<body>
<h1>DOM Example</h1>
<p id="text">This is a sample paragraph.</p>
<button onclick="changeText()">Click to Change Text</button>
<script>
function changeText() {
// Access the paragraph element and change its text content
document.getElementById("text").innerText = "The paragraph text has been updated!";
}
</script>
</body>
</html>
When a webpage is loaded, the browser creates the DOM, which represents the structure of the page. In this example, a button is provided that triggers the changeText()
function when clicked. Inside this function, document.getElementById("text")
is used to locate the paragraph element with the ID text
. Once the element is found, innerText = "The paragraph text has been updated!"
changes the content of the paragraph.
Understanding DOM-Based Redirects #
DOM-based redirects occur entirely on the client side, within the user’s browser, and are driven by JavaScript manipulating the DOM (Document Object Model). In these cases, the browser’s location is dynamically modified based on user input or URL parameters, typically using JavaScript functions like window.location
or document.location
.
Dangerous Sources and Sinks #
- Sources: In the context of DOM-based open redirects, a source is where untrusted data (such as user input, URL parameters, or cookies) enters the application. For example, if a web page uses a URL parameter to determine the redirect destination without validating it, that URL parameter becomes a dangerous source.
- Sinks: A sink is where the untrusted data is used or executed in a way that causes a harmful action, like performing a redirect. In the case, the sink is typically a function like
window.location
orwindow.location.href
, which changes the current page’s URL.
How DOM-based Open Redirects Work? #
DOM-based open redirects happen when JavaScript running in the browser manipulates the page’s location based on user input or URL parameters. Here’s a breakdown of how these redirects typically work:
-
User Input or URL Parameter:
The process begins when a user either provides input through a form field, clicks a link, or when the URL of the page contains a query parameter specifying a destination URL. For instance, a web application might allow a user to specify where they should be redirected after an action is completed. A common mechanism for this is to include a
url
parameter in the URL query string, such as?redirect=https://example.com
. -
JavaScript Manipulates the Redirect:
Once the page loads, JavaScript on the page extracts this URL parameter using methods like
window.location.search
ornew URL(window.location).searchParams.get('redirect')
. The JavaScript code processes this input and then uses it to change the page location by modifying thewindow.location
ordocument.location
object. These objects control the browser’s navigation and are responsible for performing redirects.For example, JavaScript might contain code like this:
var redirectUrl = new URLSearchParams(window.location.search).get('url'); window.location.href = redirectUrl;
Here, the
redirectUrl
is taken from theurl
query parameter in the URL, and the browser is instructed to navigate to the specified address usingwindow.location.href
. -
Lack of Input Validation:
A critical aspect of DOM-based open redirects is that many applications fail to properly validate or filter the user input (in this case, the URL parameter). Because the redirection logic relies solely on user-supplied data, an attacker can manipulate the URL parameter to redirect the user to a site of their choice, often a malicious one.
For example, if an attacker modifies the URL to look like this:
http://example.com?redirect=http://evil.com
,the JavaScript on the page will extract the
redirect
parameter, and the browser will redirect toevil.com
once the page loads. Since the user was initially onexample.com
, they may trust the site and not realize they’ve been sent to a harmful destination. -
Exploitation of the Vulnerability:
Attackers can exploit this behavior by crafting URLs that look legitimate but redirect the user to malicious websites. The attacker’s goal could be to perform phishing attacks (e.g., redirecting users to fake login pages), deliver malware, or trick users into interacting with fraudulent content.
This type of attack is particularly dangerous because the victim might not realize they have been redirected until it’s too late. Since the redirection is handled by JavaScript in the browser, it bypasses server-side security measures, such as HTTP redirects and input validation that might otherwise prevent such attacks.
Why This Happens? #
- Lack of Validation: Many applications overlook the need to check whether the destination URL is safe before redirecting the user. Without validation, the system has no way of distinguishing between a legitimate redirection and a malicious one.
- Assumption of Trust: Often, applications assume that the parameters in URLs are safe to use without proper checks. Since many sites rely on URL parameters to dynamically determine behavior (like redirection), they assume users will not attempt to abuse this mechanism.
How to Hunt for Open Redirect #
Open redirect vulnerabilities can be exploited by attackers to redirect users to malicious sites, leading to phishing attacks, session theft, and other security issues. To effectively hunt for these vulnerabilities, follow these steps:
1. Identify User-Controlled Inputs #
Start by identifying parts of the web application where user input could influence the behavior of the page, particularly URL redirects. Look for common sources of user input such as URL parameters (e.g., ?redirectTo=someurl
), cookies, hash fragments (#
), localStorage, and form inputs. These inputs could be used by JavaScript to dynamically update the browser’s location, potentially causing a redirect.
2. Review JavaScript for Location Manipulation #
Search through the JavaScript code to find instances where user input is directly used to modify the page’s location. Specifically, look for functions like window.location
, window.location.href
, window.location.replace()
, and window.location.assign()
. These functions can change the URL of the current page and can be abused if they take untrusted user input without validation.
3. Check URL Parameters Passed to JavaScript #
If you find JavaScript code that assigns a URL parameter to window.location
, test whether the value of the parameter can be manipulated. For example, a URL parameter like ?redirectTo=http://example.com
could be passed directly to window.location.href
. Test by changing the parameter to point to a malicious site (e.g., ?redirectTo=http://attacker.com
) and observe whether the site redirects to the attacker’s page.
4. Test with Common URL Schemes #
When testing for open redirects, try adding a variety of common URL schemes to user input. For example, try appending http://
or https://
to the parameter values and see if the application incorrectly redirects. If the page redirects to the specified URL (e.g., http://attacker.com
), this could indicate a DOM-based open redirect vulnerability.
5. Manipulate Hash Fragments (#
)
#
Don’t overlook the hash fragment (#
) in URLs. Some applications use hash fragments to trigger client-side changes or redirects. Try modifying the fragment part of the URL, for example, http://example.com#redirect=http://malicious.com
. If the page uses the fragment to redirect and does not properly sanitize the input, this could indicate a vulnerability.
6. Open Redirect Bypass #
A common mistake in handling open redirects is inadequate validation of user inputs. Test whether you can bypass any existing protections by manipulating redirect parameters. For instance, if an application checks if a redirect URL starts with a specific domain but does not validate subdomains or alternative encodings, try using payloads such as:
https://target.com.evil.com
https://[email protected]
Check out this cheat sheet for more examples here.
How to Prevent DOM-based Open Redirects? #
To avoid DOM-based open redirect vulnerabilities, developers should:
Validate URL Parameters #
To prevent DOM-based open redirect vulnerabilities, developers must validate URL parameters carefully. They should only allow redirection to trusted, pre-approved URLs by implementing a strict whitelist of domains. By limiting redirection destinations to a list of trusted sources, developers can ensure that malicious websites cannot be used for harmful redirects.
Sanitize Input #
When user input is involved in a redirect, developers must sanitize it thoroughly. This means filtering out any potentially dangerous content, such as harmful JavaScript code or suspicious URL schemes like javascript:
. Proper input sanitization ensures that attackers cannot inject malicious content that could compromise the integrity of the site and its users.
Avoid Direct Redirects from User Input #
Developers should avoid using user-provided data directly to manipulate window.location
or document.location
. Instead, they should validate and sanitize input before applying it. This precaution helps eliminate the risk of attackers exploiting this functionality to redirect users to malicious sites, ensuring safe browsing experiences for users.
Final Thoughts #
DOM-based open redirects occur when JavaScript in the browser uses unvalidated user input to manipulate the page’s location. This allows attackers to redirect users to malicious sites, bypassing server-side security controls. To prevent these attacks, developers should validate and sanitize all user input, particularly URL parameters. Whitelisting trusted destinations for redirects is essential to avoid exploitation.