HTTP Strict Transport Security
即 http 严格传输安全
举个例子
大部分网站如果支持 https 协议,一般的访问流程如下
- 用户输入 abc.com 后, 默认会以 http 协议访问网站服务器;
- 服务器随后响应 http 302, 告诉用户以 https 方式请求;
但因为服务器响应的这个 302 是明文的 http 包;
于是攻击者就可以中途拦截并篡改为 重定向到 恶意网站, 比如 newabc.com 或 abc1.com;
或者是篡改为 http 协议, 造成了用户 ssl 连接失败。
解决办法
服务器和客户端进行一个约定,以后的请求都走 https 加密协议, 不要再发 http 请求;
如果有关于我的 http 路径,请自动转换为 https 后再发起请求;
问题一: 约定如何告知客户端
答: 当客户端成功访问服务器的任意一次请求后, 服务器响应一个报文头,告知此约定;
问题二: 约定是否有有效期
答: 为了避免以后如域名交易或确实需要 http 通信的场景, 约定是需要一个有效期的;
由服务器的响应头内一并告知有效期;
问题三: 用户历史首次访问此服务器,并不知晓此约定,于是发起了http请求;如何避免服务器第一次响应的这个约定和302重定向不被篡改
答: 在用户第一次访问之前就提前告知用户;
办法一: 浏览器内置名单, 即 预载入列表;
服务器提前主动告知浏览器厂家将名单加入列表, 属于硬编码到浏览器中;
缺点是更新记录只能等待浏览器新版本更新;
google 维护了一个"HSTS preload list"的站点域名和子域名, 会分发给主流浏览器
可以向 https://hstspreload.appspot.com 提交申请;
办法二: 在 dns 内添加扩展, 域名解析时就确定此约定;
缺点: 支持度不高
开启 HTST 后的附带效果
原来的 https 证书如果校验错误, 用户可以在浏览器上忽略警告继续访问的。
但既然有约定加深了信任, 则浏览器便不能再忽略后续的证书错误, 以加强防护能力。
避免中间人篡改证书;
遗留问题
如果操作系统的时间被篡改到 约定 时间之后, 下此访问就会是 http 明文请求;
当然这就属于操作系统安全的问题了。
开启方法
简单来说就是,服务器的响应头需要包含 Strict-Transport-Security 字段;
例如:
Strict-Transport-Security: max-age=63072000; includeSubDomains
max-age 的含义是失效时间,此处设置为 2 年, 每次访问都会进行更新时间;
注意: 非加密传输时, hsts 字段无效;
开启效果
- 用户首次 http 访问时, 需要使用 302 重定向到 https
- 用户访问一次该 https 页面后, 浏览器便存有记录;
- 用户之后访问该 http 页面时, 直接在键入 URL 后, 浏览器便自动转为 https, 不再需要服务器再重定向;
注意: 此时是浏览器内部发生的 307 重定向
web服务器配置开启
nginx
|
|
apache2
|
|
Lighttpd 设置方法
|
|