✅ 框架与 XSS 防护概况
框架 | 是否默认转义 | 高危场景 | 建议防御措施 |
---|---|---|---|
React | ✅ 是 | 使用 dangerouslySetInnerHTML |
避免使用,必要时做内容清洗 |
Vue.js | ✅ 是 | 使用 v-html |
避免使用,或使用 DOMPurify 清洗 |
Angular | ✅ 是 | 使用 innerHTML 、bypassSecurityTrustHtml |
谨慎绕过安全策略 |
Django (模板) | ✅ 是 | 使用 ` | safe` |
Flask / Jinja2 | ✅ 是 | 使用 ` | safe` |
Spring Boot (Thymeleaf) | ✅ 是 | 使用 th:utext |
默认 th:text 安全,慎用 utext |
Express + EJS / Handlebars | ❌ 否 | 直接拼接 HTML 输出 | 使用模板语法自动转义 |
PHP 原生 / Smarty | ❌ 否 | 直接 echo 用户输入 |
使用 htmlspecialchars() + 模板转义 |
📍 React 中的 XSS 风险
⚠️ 危险代码示例:
function Comment({ content }) {
return <div dangerouslySetInnerHTML={{ __html: content }} />;
}
用户输入含
<script>
会被执行!
✅ 防御做法:
import DOMPurify from 'dompurify';
<div dangerouslySetInnerHTML={{ __html: DOMPurify.sanitize(content) }} />
📍 Vue.js 中的 XSS 风险
⚠️ 危险代码示例:
<div v-html="userContent"></div>
✅ 防御做法:
import DOMPurify from 'dompurify';
this.safeContent = DOMPurify.sanitize(userContent);
📍 Angular 中的 XSS 风险
⚠️ 危险代码示例:
this.trusted = this.sanitizer.bypassSecurityTrustHtml(userInput);
✅ 防御做法:
- 避免滥用
bypassSecurityTrustHtml
- 使用默认绑定方式或手动清洗内容
📍 Django 模板中的 XSS 风险
⚠️ 危险代码示例:
{{ comment|safe }}
✅ 防御做法:
- 避免使用
|safe
,除非你非常确信内容安全 - 默认
{{ comment }}
会自动 HTML 转义
📍 Express + EJS 模板中的 XSS 风险
⚠️ 危险代码示例:
<div><%- userInput %></div> <!-- 非转义输出 -->
✅ 防御做法:
<div><%= userInput %></div> <!-- 自动 HTML 转义 -->
📍 Spring Boot + Thymeleaf 的 XSS 风险
⚠️ 危险代码示例:
<span th:utext="${userInput}"></span>
✅ 防御做法:
<span th:text="${userInput}"></span> <!-- 自动 HTML 转义 -->
🧠 总结建议
- ✅ 默认转义机制是第一道防线,慎重绕开!
- 🚫 避免使用不安全输出语法如
|safe
、v-html
、dangerouslySetInnerHTML
等 - 🧼 推荐使用 DOMPurify 对富文本内容做清洗
- 🔐 后端应区分内容用途,做针对性输出处理
📌 推荐工具
- 富文本清洗:
DOMPurify
、xss
(Node.js 库)