Skip to content
Security
Skill

/postmessage-xss

Detect postMessage handlers that trust unvalidated origins or write attacker-controlled data to dangerous DOM sinks.

From plugin
vuln-scout
2535 skills9 agents15 commands

Claude Code

$ npx -y skills add allsmog/vuln-scout --skill postmessage-xss --agent claude-code

SKILL.md

postmessage-xss.SKILL.md
name: postmessage-xss
description: >-
  Detect postMessage handlers that trust unvalidated origins or write
  attacker-controlled data to dangerous DOM sinks.
version: 1.0.0

DOM XSS via postMessage

This skill covers detecting and exploiting Cross-Origin Messaging (postMessage) vulnerabilities that lead to DOM-based XSS.

---

Overview

`postMessage` is a browser API that allows cross-origin communication between windows/iframes. When message handlers don't validate `event.origin`, any website can send malicious data that may execute as XSS.

**Why This Is Critical:**

  • Often overlooked by security scanners (server-focused)
  • Enables XSS from any origin without user interaction
  • Commonly chained with SSRF/bot scenarios to bypass localhost restrictions

---

Vulnerability Pattern

Vulnerable Code

A handler that accepts messages from ANY origin and writes to DOM:

window.addEventListener("message", (event) => {
    const data = event.data;
    document.getElementById("output")[".inner" + "HTML"] = data.html;  // XSS!
});

Secure Code

window.addEventListener("message", (event) => {
    if (event.origin !== "https://trusted-domain.com") {
        return; // Reject untrusted origins
    }
    document.getElementById("output").textContent = data.text; // Safe
});

---

Detection Patterns

Step 1: Find Message Handlers

# Find all postMessage event listeners
grep -rniE "addEventListener\s*\(\s*['\"]message['\"]" --include="*.js" --include="*.ts" --include="*.html"

# Find direct onmessage assignments
grep -rniE "\.onmessage\s*=" --include="*.js" --include="*.ts"

Step 2: Check for Missing Origin Validation

# Find handlers and check next 10 lines for origin check
grep -rniE "addEventListener\s*\(\s*['\"]message['\"]" --include="*.js" --include="*.ts" -A 10 | grep -v "origin"

Step 3: Trace to Dangerous Sinks

# event.data to DOM write sinks
grep -rniE "event\.data.*(inner|outer)HTML" --include="*.js" --include="*.ts"

# event.data to location (open redirect)
grep -rniE "event\.data.*location|location.*event\.data" --include="*.js" --include="*.ts"

# event.data assigned to variable (trace further)
grep -rniE "=\s*event\.data" --include="*.js" --include="*.ts"

---

Common Vulnerable Patterns

| Pattern | Risk | Detection | |---------|------|-----------| | No origin check + DOM sink | Critical | Missing `event.origin` validation | | Weak origin check (regex) | High | `origin.includes()` or `origin.match()` | | Variable assignment then sink | High | `const data = event.data` then later to sink | | jQuery `.html()` method | Critical | `$(elem).html(event.data)` |

---

Exploitation via SSRF + iframe

When combined with SSRF (bot visits attacker URL):

1. Bot visits attacker page 2. Attacker page creates iframe to `http://localhost:1337/` 3. postMessage sends XSS payload to iframe 4. XSS executes in localhost context (bypasses network restrictions)

This chain bypasses Chrome's Private Network Access restrictions.

---

Remediation

1. Always Validate Origin

const ALLOWED_ORIGINS = ["https://trusted.com"];

window.addEventListener("message", (event) => {
    if (!ALLOWED_ORIGINS.includes(event.origin)) {
        return; // Reject
    }
    // Process message safely...
});

2. Use Safe Sinks

  • Use `textContent` instead of HTML sinks
  • Use DOMPurify to sanitize HTML content
  • Validate message structure before processing

3. Add Frame Protection

X-Frame-Options: SAMEORIGIN
Content-Security-Policy: frame-ancestors 'self'

---

References

  • OWASP: DOM-based XSS
  • CWE-79: Improper Neutralization of Input
  • PortSwigger: DOM-based XSS via postMessage
Read more
@allsmog
Ships withvuln-scout

AI-powered whitebox penetration testing plugin for Claude Code. 9 languages, 22 skills, 7 autonomous agents. STRIDE threat modeling, OWASP 2025 coverage, polyglot monorepo support.

2535 skills9 agents
Get the whole plugin

Stars on GitHub

Momentum

stars in total
25
Star history of allsmog/vuln-scout on GitHub, a chart by star-history.com

Other skills on vuln-scout.

ai-ml-attacks

ai-ml-attacks

This skill should be used when the user asks about "AI security", "ML pipeline attacks", "prompt injection", "model…

@allsmog@allsmogInstall Skill
business-logic

business-logic

This skill should be used when the user asks about "business logic", "workflow vulnerability", "trust boundary", "state machine",…

@allsmog@allsmogInstall Skill
cache-poisoning

cache-poisoning

This skill should be used when the user asks about "cache poisoning", "web cache deception", "CDN cache", "proxy cache", "nginx…

@allsmog@allsmogInstall Skill
cloud-native

cloud-native

This skill should be used when the user asks about "cloud security", "AWS security", "GCP security", "Azure security",…

@allsmog@allsmogInstall Skill
compliance-mapping

compliance-mapping

This skill should be used when the user asks about "compliance mapping", "PCI-DSS", "HIPAA", "SOC 2", "NIST CSF", "regulatory…

@allsmog@allsmogInstall Skill
cpg-analysis

cpg-analysis

This skill should be used when the user asks about "Code Property Graph", "CPG analysis", "Joern queries", "CPGQL", "data flow…

@allsmog@allsmogInstall Skill

More skills from other plugins.

api-security

api-security

Use for authorized security assessment of REST, GraphQL, WebSocket, or SOAP APIs, including discovery, authentication,…

@zhaoxuya520@zhaoxuya520Install Skill
nemoclaw-user-guide

nemoclaw-user-guide

Find official NemoClaw documentation for installation, configuration, operation, or troubleshooting. Also handles requested docs…

nemoclaw11d23k
@nvidia@nvidiaInstall Skill

Questions about postmessage-xss.

Which coding agents can use postmessage-xss?
postmessage-xss installs in Claude Code, Codex, Cursor, Gemini CLI, GitHub Copilot, OpenCode and Windsurf with the skills CLI, using each agent's flag shown on this page. Flowy's auto-invocation, which fires a skill when your prompt matches, runs in Claude Code only.