神奇的 421 Misdirected Request

这几天在折腾服务的时候,出现了几次421现象,一开始没注意,后面复现多次出现,于是查了一下,有点意思。

场景

  • 同一台web服务器上启动多个服务;
  • 多个服务通过 Nginx 转发,监听同一个接口;
  • 多个服务使用的证书相同,同一张通配符;

当我在手机 Chrome 访问 https://razeen.cn 后 立马切换到 https://med.razeen.cn 时,偶尔就会出现 421, 刷新缓存,或在新的无痕窗口中就不会有问题。

原因

Google 一下, 在 serverfault 上看到有人提了类似问题,有人详细回答的造成这种现象的一系列原因:

  1. 服务端和客户端都支持和使用了 HTTP/2;

  2. 客户端请求页面 foo.example.com;

  3. 在 TLS 协商的时候,服务端提供的通配符或多域名证书,这张证书对 foo.example.combar.example.com 两个域名都有效的(且客户端信任该证书)。

  4. 客户端请求 bar.example.com 时重用连接;

  5. 服务端不能或不允许跨域名的连接复用(例如配置不同或服务端强制TLS重协商), 于是返回421;

  6. 客户端不会自动使用新连接重试(如 Chrome Bug #546991, 已修复)。 在相关的RFC中没有严格的规定客户端在收到401后一定需要重试。重试失败对用户不是特别友好,但对于调试工具或 HTTP 库来说可能是可取的。

最后还建议每个域名用不同的证书,或者完全关闭 HTTP/2.

本文链接:参与评论 »

--EOF--

Comments