浏览器 Web 安全基础系列
防盗链到底防什么(当前篇)
盗链指其他网站直接引用你的图片、视频或下载地址,内容显示在对方页面,带宽却由你的服务器或 CDN 承担。最基础的防盗链检查 Referer;私有资源则需要真正的权限校验或短期签名 URL。

Referer 防盗链
其他网站引用:
<img src="https://cdn.example.com/images/photo.webp">
浏览器向你的 CDN 请求时可能发送:
Referer: https://other.example/article
服务器允许自己站点,拒绝其他来源:
const allowedHosts = new Set(['www.example.com', 'blog.example.com']);
function allowedReferer(req) {
const referer = req.headers.referer;
if (!referer) return false;
try {
return allowedHosts.has(new URL(referer).hostname);
} catch {
return false;
}
}
Nginx 示例:
location ~* \.(jpg|jpeg|png|webp|gif)$ {
valid_referers server_names *.example.com;
if ($invalid_referer) {
return 403;
}
}
空 Referer 怎么处理
用户直接在地址栏打开资源、隐私策略、浏览器插件或协议降级都可能导致 Referer 缺失。
允许空 Referer:兼容性更好,但更容易绕过;
拒绝空 Referer:更严格,但可能误伤下载、客户端和分享场景。
普通博客图片通常可以允许空 Referer并拒绝明确的外站来源;高价值资源不要只靠 Referer。
Referer 可以伪造
浏览器页面脚本不能随便设置 Referer,但 curl、下载器和攻击者服务器可以:
curl -H "Referer: https://www.example.com/" https://cdn.example.com/images/photo.webp
所以 Referer 防盗链主要防“网页直接引用”,不是强身份认证,也防不了有意下载。
签名 URL
私有文件可以生成带过期时间和 HMAC 的地址:
/download/report.pdf?expires=1783900000&signature=...
服务端签名:
import crypto from 'node:crypto';
function sign(path, expires, secret) {
return crypto
.createHmac('sha256', secret)
.update(`${path}:${expires}`)
.digest('base64url');
}
验证时检查过期时间和签名:
function verify(path, expires, supplied, secret) {
if (Date.now() >= Number(expires) * 1000) return false;
const expected = sign(path, expires, secret);
const a = Buffer.from(expected);
const b = Buffer.from(String(supplied || ''));
return a.length === b.length && crypto.timingSafeEqual(a, b);
}

签名必须覆盖资源路径和过期时间,否则攻击者可能把有效签名换到另一个文件上。还可以绑定用户 ID、资源 ID、清晰度或下载次数,但绑定 IP 容易误伤移动网络和代理用户。
登录鉴权与签名 URL 的关系
业务服务先检查用户是否有权访问文件,再签发短期 URL:
用户请求下载
→ 业务服务验证登录和资源权限
→ 生成 5 分钟签名 URL
→ CDN/资源服务验证签名
→ 返回文件
签名 URL 不是权限判断本身。服务端不能只要用户知道 fileId 就签发地址,仍要检查资源归属和角色权限。
为什么图片常用 URL 签名而不是 Authorization 头
<img>、<video> 和下载链接不方便统一添加自定义 Authorization 请求头。Cookie 或签名 URL 更适合浏览器原生资源标签。API 数据则更常使用 Cookie Session 或 Bearer Token。
视频保护
HLS 视频包含播放列表、分片、字幕和可能的密钥:
master.m3u8
segment-001.ts
segment-002.ts
key
只保护主 m3u8 不够,分片地址仍可能被下载。常见组合:
CDN Token 鉴权;
短期签名 URL 或签名 Cookie;
分片和密钥鉴权;
DRM;
用户水印;
并发、速率和异常下载检测。
任何能在终端播放的内容都无法保证绝对不可复制,目标是提高成本、限制规模和保留追踪能力。
防盗链与 CORS
CORS 控制 JavaScript 是否能读取跨源响应。<img> 即使没有 CORS 许可,也可能正常显示跨源图片。因此 CORS 不能替代防盗链。
Referer 防盗链决定是否返回资源;签名 URL 和登录鉴权决定请求是否获得授权。这三者层级不同。
选型建议
常见误区
防盗链等于防下载
不对。资源最终到达用户设备,只能增加滥用成本,不能保证不可复制。
URL 足够复杂就安全
隐藏地址不是授权。应使用不可伪造签名和服务端权限校验。
签名 URL 有效期越短越好
太短会导致弱网、断点续传和长视频播放失败,需要按资源大小和播放模式设计续签机制。
小结
Referer 防盗链适合减少普通网页盗用;签名 URL 适合限制链接构造和有效时间;登录鉴权负责判断用户是否有权限。高价值资源通常需要三层以上组合,而不是寻找“绝对防下载”的单一技术。
参考资料
防盗链到底防什么:Referer、签名 URL 与 CDN 鉴权
https://lautung.com/archives/web-security-12-hotlink-signed-url
评论