踩坑记:HSTS导致子域名无法访问

HSTS是把双刃剑,但是当SSL证书并不是通配符证书时,子域名等都是无法访问的。

一、背景

    项目A是二级域名,并且使用 HTTPS 访问,

    子项目B使用的是基于该二级域名的三级域名,仅使用 HTTP 访问,

    但是上线后发现项目B访问的时候出现下图的错误。

        reject-hsts01.png

    点开高级,会看到下图的信息,见红框中的 HSTS,

        reject-hsts02.png

    另外,查看控制台的 network,产生了两次请求,而且第一次请求居然被 307了,黑人问号脸?

        reject-hsts03.png

    然后查看项目A的 network,发现 response headers 中有 HSTS 的信息。

        reject-hsts04.png

    好了,所有的证据都指向一个点:HSTS,所以就来搞清楚这个 HSTS 待敌是啥玩意儿。


</p>

二、知识点

    1、什么是 HSTS

        国际互联网工程组织IETF正在推行一种新的Web安全协议

        全称是:HTTP Strict Transport Security

        作用:简言之就是浏览器端会将 http 请求强制转为 https 请求,从此服务器端再也不要再进行重定向操作了。

        开启:当客户端发起 HTTPS 请求后,服务端返回的超文本传输协议响应头中包含 Strict-Transport-Security 字段,

            如:Strict-Transport-Security: max-age=31536000; includeSubDomains

            这说明:① 在未来的 31536000秒(一年)内,HSTS 都是生效的,即该域名的 http 请求都将自动转为 https 请求;② includeSubDomains 意味着该域名下的所有子域名也都会采用 https 请求

    2、弊端

        ① 当 Strict-Transport-Security 还未过期,但是域名的证书已经过期了,此时处于 HSTS 考虑,浏览器仍然会采用 https 的方式访问,即会提示不安全</span>

        ② 当主域名的证书并不是通配符证书时,此时子域名会强制走 HSTS,所以也会提示不安全,无法访问
</span>

        ③ 虽然 HSTS 有效抵御了一些不安全的问题(下文会提到),即所有的请求都是走的 HTTPS,但是首次访问的时候走的是 HTTP 协议(暂不考虑Preload List),黑客也是有机可乘的
</span>

        ④ Strict-Transport-Security 过期之后的首次请求,走的又是 HTTP 协议</span></span>

    3、优势
</span>

        不仅仅是优势,其实也是最大的安全技术:HSTS可以用来抵御SSL剥离攻击。</span>

        何为SSL剥离攻击?就是说人们访问站点的时候,一般都是使用的 HTTP 请求,然后再由服务端进行重定向操作,此时攻击者将用户访问的所有 HTTPS 协议的地址转为 HTTP 协议的地址,从而达到阻止HTTPS的目的,简言之就是偷偷地将目标地址换成指向指定的类似钓鱼网站等地址。

        而 HSTS 的作用就是,当浏览器和服务端创建过一次安全连接后,之后所有的请求便都会转换成 HTTPS 协议的请求。


三、解决

    我们现在的问题不是要去添加 HSTS,而是要去取消 HSTS。

    从浏览器到服务端,其实中间最主要经过的就是 nginx。

    1、处理 nginx

        修改 nginx 的配置配置文件,发现根本就没有配置 Strict-Transport-Security ,于是就手动添加一行配置,将时间设置为 1 秒,

            reject-hsts05.png

        重启后发现了神奇的事情,查看 network 的时候,发现响应头信息中有两条 Strict-Transport-Security,又是黑人问号脸。推断其中时间为1秒的应该是nginx中的配置。

            reject-hsts06.png

        所以,修改 nginx 配置是行不通的

    2、终极解决之道

        中间又踩了一些坑,最后发现,应该是去调整服务端的响应头信息,

        服务端主体技术是 springBoot,安全框架是 springSecurity,然后又踩了一波坑,最后发现,其实只要调整的是 springSecurity 中的配置。</span>

        配置见官网,点击链接
</span>

        配置也很简单,见下图即可。

            reject-hsts07.png


四、后续

    按照上文所述调整,理应完事大吉,但访问子域名的时候还是会有问题,这和浏览器的缓存有关系,那么此时,我们需要调整下浏览器。

    此处仅以 Chrome 为例,

    1、访问chrome://net-internals/#hsts

    2、见下图操作

        reject-hsts08.png














------ 本文结束 感谢阅读 ------
0%