https下防盗链核心是签名不可篡改与过期时间不可绕过;需前后端签名规则一致、密钥保密、$uri带前导/、$arg_e用秒级时间戳、绑定ip时确保真实地址透传,并采用url安全base64编码。

在 HTTPS 环境下用 secure_link_md5 实现时效性防盗链,核心不是“加 HTTPS”本身,而是确保签名逻辑、时间校验和传输过程在加密通道中仍保持完整可信。HTTPS 只负责传输加密,不改变 Nginx 的校验行为;真正起防盗作用的,是签名不可篡改 + 过期时间不可绕过。
签名规则必须前后端完全一致
服务端(生成链接)与 Nginx(校验链接)拼接签名原文的字段、顺序、编码方式必须一字不差:
- 密钥(
secret_key)需严格保密,不能硬写在前端或日志中 -
$uri必须带前导/,且不含查询参数(如/download/report.pdf,不是/download/report.pdf?e=...) - 过期时间
$arg_e是秒级 Unix 时间戳(如1717027200),不是毫秒,也不是格式化时间字符串 - 若绑定客户端 IP(推荐),Nginx 配置中要写
$remote_addr,生成链接时也必须用同一 IP —— 若有反向代理,需通过$http_x_forwarded_for并确保该头可信(配合set_real_ip_from)
Nginx 配置要放在 location 块内,且响应逻辑清晰
以下是一个生产可用的 HTTPS 资源保护配置示例(保护 /dl/ 下所有文件):
location /dl/ {
secure_link $arg_st,$arg_e;
secure_link_md5 "my_2026_secret$uri$arg_e$remote_addr";
<pre class="brush:php;toolbar:false;">if ($secure_link = "") { return 403; }
if ($secure_link = "0") { return 410; }
alias /var/www/assets/;}
说明:
- 不用
root而用alias,避免路径拼接错误(alias /path/末尾斜杠必须保留) - 返回
410 Gone而非403 Forbidden给过期请求,语义更准确,也利于客户端缓存控制 - HTTPS 不影响
$remote_addr获取,但若前端有 CDN 或 LB,需提前透传真实 IP
生成链接时注意 HTTPS 协议与 Base64 URL 安全编码
合法链接形如:
https://example.com/dl/app.zip?st=KvXqLzR8YmJkNzE2MzQ1&e=1717027200
其中:
- 协议必须为
https://(防止中间人篡改参数或降级到 HTTP) -
st是对"my_2026_secret/dl/app.zip1717027200192.168.1.100"做 MD5 后,再经base64.urlsafe_b64encode编码、并去除末尾=的结果 - 不能用普通 Base64,必须用 URL 安全变体(
+→-,/→_)
关键安全增强点
仅靠时间戳 + 密钥还不够防转发,建议至少叠加一项:
-
绑定用户粒度:后端生成链接时注入唯一标识(如
uid_123),Nginx 改为secure_link_md5 "uid_123:my_2026_secret$uri$arg_e" -
限制单次使用:Nginx 无法直接实现,需后端记录已用签名 + Redis 去重,但可配合
secure_link先做时效拦截 - 统一服务器时间:Nginx 与生成服务必须 NTP 同步,误差建议控制在 2 秒内,否则易误判过期











