Referer检查防CSRF真的可靠吗?为什么我设置了还是被绕过?

朱莉🍀 阅读 56

我们后端加了Referer检查来防CSRF,但测试时发现攻击者用空Referer或者同域跳转就能绕过。我前端也试过加一些header,但好像没用。是不是这种防护方式本身就不太靠谱?

另外,我在页面里用了下面这段CSS做基础样式隔离,会不会影响安全策略?

body {
  margin: 0;
  padding: 0;
  font-family: -apple-system, BlinkMacSystemFont, sans-serif;
}
button {
  cursor: pointer;
  border: none;
  background: #007bff;
  color: white;
}
我来解答 赞 7 收藏
二维码
手机扫码查看
2 条解答
慕容玉曼
你这个问题问对了,Referer检查确实不靠谱。空Referer、同域跳转、甚至浏览器隐私策略都会让它失效,早该换了。

直接上CSRF Token方案,这是目前最靠谱的:

后端生成Token存Session,前端页面获取后放表单隐藏域或请求头:

// 后端生成Token
session_start();
if (empty($_SESSION['csrf_token'])) {
$_SESSION['csrf_token'] = bin2hex(random_bytes(32));
}
$csrf_token = $_SESSION['csrf_token'];

// 验证Token
function verify_csrf($token) {
return hash_equals($_SESSION['csrf_token'], $token);
}


// 前端获取Token并发送请求
const csrfToken = document.querySelector('meta[name="csrf-token"]').content;

fetch('/api/action', {
method: 'POST',
headers: {
'Content-Type': 'application/json',
'X-CSRF-Token': csrfToken
},
body: JSON.stringify({data: 'xxx'})
});


或者更简单的,直接给Cookie加SameSite属性(前提是你不用跨域场景):

// 设置SameSite Cookie
session_set_cookie_params([
'lifetime' => 0,
'path' => '/',
'domain' => '',
'secure' => true,
'httponly' => true,
'samesite' => 'Strict' // 或 Lax
]);
session_start();


你那段CSS跟安全完全没关系,样式隔离防不了CSRF,别指望它。

总结:Referer检查就是个心理安慰,早换Token吧。
点赞
2026-03-18 21:09
西门文轩
问题应该出在你只依赖 Referer 做 CSRF 防护上——这玩意儿本身就不是设计来防 CSRF 的,只是顺带能挡一挡低级攻击。

Referer 是浏览器自动带的请求头,但浏览器在某些场景下会丢掉它:比如从 HTTPS 跳到 HTTP、用户手动设置隐私选项、某些插件会清空、或者攻击者用 直接触发 POST(老浏览器可能不带 Referer)。更别说现在同源跳转+postMessage 或者利用 CORS 的方式都能绕过 Referer 校验。

真正靠谱的 CSRF 防护得靠:
- 后端用 Anti-CSRF Token(比如生成一个随机 token 放在表单或 header 里,后端比对)
- 或者设置 SameSite Cookie 属性(SameSite=StrictLax
- 如果必须用 Referer 校验,也得配合白名单逻辑,不能只判断“是否为空”这种弱逻辑

你提到的那段 CSS 完全不影响安全策略——marginpaddingfont-family 这些纯样式声明不会引入任何 XSS 或 CSRF 风险。除非你动态注入了