关于 csrf-protection
csrf-protection 是一项 CSRF 防护技能,面向实现 Web 应用安全的开发者。它介绍同步令牌、双重提交和 SameSite Cookie 等防护方式及实践要点。
主要功能
- 01同步令牌验证
- 02双重提交 Cookie
- 03SameSite Cookie 防护
- 04Origin/Referer 校验建议
- 05Express 与 Flask-WTF 示例
适用场景
- 01为状态变更请求加入 CSRF 防护
- 02在表单中集成令牌验证
- 03检查 Cookie 与请求来源设置
安装
复制下面的命令,在终端中运行。
$
npx skills add https:/ / github.com/ secondsky/ claude-skills --skill csrf-protection安装后在 Claude Code 中输入/csrf-protection确认已加载。
附带文件references/python-react.md
详细介绍
CSRF 防护
通过多层防护抵御跨站请求伪造攻击。
防护方法
| 方法 | 工作原理 | 浏览器支持 |
|---|---|---|
| 同步器令牌 | 隐藏表单字段,由服务器端验证 | 全部 |
| 双重提交 | Cookie 和标头必须匹配 | 全部 |
| SameSite Cookie | 浏览器阻止跨源请求 | 现代浏览器 |
基于令牌的防护(Express)
const crypto = require('crypto');
function generateToken() {
return crypto.randomBytes(32).toString('hex');
}
// Middleware
app.use((req, res, next) => {
if (!req.session.csrfToken) {
req.session.csrfToken = generateToken();
}
res.locals.csrfToken = req.session.csrfToken;
next();
});
// Validation
app.post('*', (req, res, next) => {
const token = req.body._csrf || req.headers['x-csrf-token'];
// crypto.timingSafeEqual throws RangeError when buffers differ in length,
// so check length explicitly first (still constant-time on the equal-length path).
const csrf = req.session.csrfToken || '';
if (!token || token.length !== csrf.length) {
return res.status(403).json({ error: 'Invalid CSRF token' });
}
if (!crypto.timingSafeEqual(Buffer.from(token), Buffer.from(csrf))) {
return res.status(403).json({ error: 'Invalid CSRF token' });
}
next();
});
SameSite Cookie
app.use(session({
cookie: {
httpOnly: true,
secure: true,
sameSite: 'strict', // or 'lax'
maxAge: 3600000
}
}));
HTML 表单集成
<form method="POST" action="/transfer">
<input type="hidden" name="_csrf" value="<%= csrfToken %>">
<button type="submit">Submit</button>
</form>
最佳实践
- 应用于所有会更改状态的请求(POST、PUT、DELETE)
- 对敏感 Cookie 使用 SameSite=Strict
- 验证 Origin/Referer 标头
- 切勿使用 GET 执行修改操作
- 设置令牌过期时间(通常为 1 小时)
- 结合多层防护
其他实现
请参阅 references/python-react.md,了解:
- Flask-WTF 完整 CSRF 设置
- 用于管理 CSRF 令牌的 React hooks
- 双重提交 Cookie 模式
常见错误
- 认为身份验证可以防止 CSRF
- 在多个会话间重复使用令牌
- 将令牌存储在 localStorage 中
- 未设置令牌过期时间
评论
支持 Markdown