We apologize that the translated content is not provided to this page.
前言
由于需要提高访问例如Github、Cloudfront等网站速度,防止SNI阻断的情况,搭建了一个SNI代理,可以处理根据SNI进行转发。
使用SNI代理的好处就是不改变SSL证书,全程透明,这是比Nginx反向代理自签名证书更好的方案。
flowchart LR;
A[客户端]-->B[SNI代理];
B-->C[Github];
B-->D[Cloudfront];
问题
目前出现问题:长时间闲置Github后再次访问会导致出现如下状况。
问题分析
尝试
更换SNIProxy软体,由C语言版本的dlundquist/sniproxy,变更为go版本的SNIProxy:TachibanaSuzume/SNIProxyGo。
发现并无效果。
深入排查
- 通过排查服务端情况,发现服务端映射端口:
6653
-->alive.github.com
、6654
-->github.com
; - 再次访问Github时,端口
6654
(github.com)已被关闭,流量经过6653
(alive.github.com)端口发送(即发送流量端口非正确的域名,导致出现错误);
问题梳理
-
由于长连接Keep-Alive的原因;
-
客户端浏览器,由于SNI代理为同一IP,导致浏览器误认为连接可以复用(实测经过清理socket后重新建立连接可以正常访问);
flowchart LR; A[浏览器]-->B[SNI代理]-->C[端口6654]-->D[github.com:443]-.-E[140.82.112.3]; B-->F[端口6653]-->G[api.github.com:443]-.->H[140.82.112.25];flowchart LR; A[浏览器]--端口复用-->B[SNI代理]--连接无保持正常断开-->C[端口6654]--X-->D[github.com:443]-. X .-E[140.82.112.3]; B--github.com流量转发到这-->F[端口6653]-->G[api.github.com:443]-.-H[140.82.112.25]; -
泛域名证书应该也是问题原因之一;
疑惑部分
- 发送流量出错后,为何加密返回的数据能够正常解析?(经查,证书为泛域名证书,可以正常解析内容)
问题解决思路
- 服务端显式设置连接超时时间(对大文件传输、连接响应慢并不友好,但是能更快恢复访问阻止复用)
- 关闭Keep-Alive功能(由于数据对于代理服务器未知,无法进行篡改)
- 二次判断SNI(由于证书相同,多个TLS握手仅需一次后传输直接进行复用,无法进行判断)
- 服务端不主动关闭连接
- 维护一个相同证书服务器的列表,判断列表内连接减少后直接中断全部连接
- 待续...