V2EX = way to explore
V2EX 是一个关于分享和探索的地方
现在注册
已注册用户请  登录
fancy20
V2EX  ›  站长

被 http2 坑了一把,nginx 1.9.15/1.10.0 + http2 + post + safari 有严重 bug

  •  
  •   fancy20 · 2016-08-20 08:11:06 +08:00 · 20825 次点击
    这是一个创建于 3018 天前的主题,其中的信息可能已经有所发展或是发生改变。
    惭愧在公司官网上了 http2 ,有一部分注册 post 请求发送时返回错误 0x0 ,后来通过错误回调的统计发现大部分是 safari(好像还有 edge)出现这个问题, safari 能稳定复现, chrome 不能复现,关闭 http2 后 safari 不能复现。

    具体就是,打开 http2 站点页面,等待几分钟不动(或看下面连接里说可以断网再连接上),接下来在页面上的操作,比如我们的注册是 ajax 的 post 请求会返回 0x0 错误,看 safari 的调试页面网络请求都没发。贴两个连接:

    https://openradar.appspot.com/26406397
    http://stackoverflow.com/questions/37309940/nginx-http-2-http-post-safari-error

    猜测是 safari 的 http2 socket 超过 idle 后,即使有新请求也不会重新连接,直接报连接错误。。

    这次给我的教训就是生产环境还是不要玩这类太新的东西了。。

    @qgy18
    27 条回复    2017-07-12 21:58:08 +08:00
    fancy20
        1
    fancy20  
    OP
       2016-08-20 08:13:22 +08:00
    问题就是导致用户打开我们官网,上来就直接注册没问题。但他看了一会儿官网介绍,再注册就提示错误了。。看了从 5 月份上了 http2 后就有这类错误发生,但一直没察觉,看统计大约有 100 多次。。
    bigzhu
        2
    bigzhu  
       2016-08-20 08:49:41 +08:00
    我有类似问题,主要是图片加载上,图太多的时候,不再会等着慢慢加载,似乎迅速 timeout ,后面的直接提示错误(忘记错误码了),显示加载失败。
    MrMario
        3
    MrMario  
       2016-08-20 09:49:08 +08:00 via iPhone
    具体哪个 Safari 版本?
    ivmm
        4
    ivmm  
       2016-08-20 10:06:22 +08:00
    不新了吧, Nginx 支持 h2 都已经有个一年了。
    FrankFang128
        5
    FrankFang128  
       2016-08-20 10:27:59 +08:00 via Android
    什么是 0x0 错误
    fancy20
        6
    fancy20  
    OP
       2016-08-20 10:34:27 +08:00 via iPhone
    @MrMario 公司两个用 mac 的同事自带的 Safari 都可复现,版本应该比较新,具体我之后看看

    @FrankFang128 提示大意是无法连接服务器,错误码 0x0
    qgy18
        7
    qgy18  
       2016-08-20 11:06:37 +08:00   ❤️ 2
    @fancy20
    是有这个问题,我之前也遇到了,还研究了一下,我争取本周末写一个文章详细介绍下这个问题。
    这个是 nginx 的锅,应该跟 http/2 关系不大。

    https://trac.nginx.org/nginx/ticket/959#comment:18
    https://blog.crashed.org/fixing-nginx-bugs-with-nghttp2/
    qgy18
        8
    qgy18  
       2016-08-20 11:22:39 +08:00
    要避免这个问题,要么升级到 nginx 1.11.0+(第二位奇数表示是 nginx 的主线版本,偶数是稳定版本);要么使用 nghttp2 等其它软件做为 http/2 接入层。

    两者风险都挺大的,建议楼主先在生产环境关闭 http/2 。
    ThreeBody
        9
    ThreeBody  
       2016-08-20 11:23:44 +08:00 via Android
    我之前用 lnmp.org 的一键安装包安装的 nginx ,用 httpt2 后,如果目录后面没有 /就会出现 504 gateway time out ,我一直以为是我自己配置错了,最试了一下用 ssl ,所有问题都消失了
    后来干脆不用 http2 了
    kn007
        10
    kn007  
       2016-08-20 11:25:39 +08:00
    一直用新版,没有啥问题
    rrfeng
        11
    rrfeng  
       2016-08-20 12:18:43 +08:00
    这个我遇到过。

    我们的现象是 iOS 客户端在发起 POST 请求的时候很大概率会直接失败。

    就是 http2 在建立连接的时候一个预发送数据的窗口问题,很难说是谁的错…… nginx 并没有违反协议,但是和 http client 采取了不同的策略。

    所以 1.11 加了一个新的配置项。
    LazyZhu
        12
    LazyZhu  
       2016-08-20 12:27:11 +08:00
    哎呀,可在 1.10.x 打补丁啊
    qgy18
        13
    qgy18  
       2016-08-20 12:38:34 +08:00
    @rrfeng

    To avoid unnecessary latency, clients are permitted to send additional frames to the server immediately after sending the client connection preface, without waiting to receive the server connection preface.

    客户端可以在建立连接的时候发送其它帧(也应该包括 DATA 帧),但是 Nginx 这时候的 initial window 是 0 ,所以回了一个 REFUSED_STREAM ,这时候部分浏览器直接报错而不是重试。

    格式感觉这还是 Nginx 的锅。


    @LazyZhu

    Nginx 已经明确表示,这个补丁不会移植到 1.10.x 。他们认为: 1.10.x 是稳定版,而 HTTP/2 本来就属于「不稳定」的功能,要用 HTTP/2 就上主线版。

    We don't backport features to the stable branch (that's what we call stable, no enhancements). It receives only critical bug fixes. If you use such new, very complicated and actively developing protocol as HTTP/2 then it's naturally that you have to stay with the mainline branch.
    anjunecha
        14
    anjunecha  
       2016-08-20 12:38:56 +08:00 via iPhone
    之前遇到过,后来索性在服务器上就去掉了 http2
    just1
        15
    just1  
       2016-08-20 12:57:44 +08:00 via Android
    一直在用 1.9.7 ,会有这个问题嘛
    rrfeng
        16
    rrfeng  
       2016-08-20 13:10:28 +08:00
    @just1 1.9.7 没有
    rrfeng
        17
    rrfeng  
       2016-08-20 13:10:49 +08:00
    1.10 就不能用了
    或者自己打 patch
    反正 1.11 也发布了
    fancy20
        18
    fancy20  
    OP
       2016-08-20 13:48:30 +08:00 via iPhone
    @qgy18 已经关了,当时觉得稳定版应该没太大问题了就开了,否则也不会去掉 spdy 啊

    太难了…甚至想去掉 https 降到 http 了,改 https 导致了一大堆问题,已经因此荣登公司“持续最久”,“引发问题最多” bug 榜榜首。之前在某度的时候,搜索改 https 有个 http 引用的问题找到我,一堆人催着赶紧解决,本来就很忙还催的要命,当时很生气,现在总算明白了…
    rrfeng
        19
    rrfeng  
       2016-08-20 13:50:59 +08:00
    @fancy20
    这个 bug 确实隐蔽性很高,而且我们不知道为什么只有 iOS 的库有问题,而且当且仅当是 WiFi 的时候。
    可能是移动网络无法 upgrade 到 http/2 ?
    fancy20
        20
    fancy20  
    OP
       2016-08-20 14:02:16 +08:00 via iPhone
    @qgy18 ssl 太难了…我们有个模块是用户申请注册后给用户发邮件的,用的 javamail 和腾讯企业邮箱,上个月突然有一天同事说最近 3 天都没人注册啊(邮件会抄送他邮件组),然后发现是邮件都没发出去,在服务器上打了一堆 java 网络日志都是握手失败,但我 mac 同样代码就没问题。。最后发现服务器用的 jdk 是 1.8.51 ,我 mac 是 1.8.45 ,腾讯改了 ssl 配置,他新的 cipher 在 1.8.51 被 Oracle 改为不安全已废弃的,各种参数显式指定使用都不行,换了 1.8.45 的 sdk 解决。。腾讯为啥要改呢, Oracle 为啥要改呢。。。太难了
    fancy20
        21
    fancy20  
    OP
       2016-08-20 14:05:10 +08:00 via iPhone
    @rrfeng 不是,在 MacBook 上的 Safari 稳定复现,但 chrome 没问题。根据统计 edge 可能也有问题,但我们没测试
    qgy18
        22
    qgy18  
       2016-08-20 14:19:57 +08:00   ❤️ 1
    https://imququ.com/post/nginx-http2-post-bug.html

    好了,文章写好了。

    非常感谢 @fancy20 提供这一信息,我之前一直以为 Nginx 是在主线版和稳定版同时修复的这个问题。
    今天才发现, Nginx 当前稳定版根本就没修,这太危险了。

    btw , https 是会引入一堆新问题,但现在运营商已经越来越没节操,再难也得上啊。
    fancy20
        23
    fancy20  
    OP
       2016-08-20 14:27:31 +08:00 via iPhone
    @qgy18 分析透彻,赞!经常打开你的博客看,感觉文章都很用心
    fcicq
        24
    fcicq  
       2016-08-20 15:35:02 +08:00
    这只能证明不用来自 HTTP2 JP 社区的实现, 后果自负.
    hyuwang
        25
    hyuwang  
       2016-08-21 03:09:06 +08:00
    感谢...LZ 救了我
    差点也准备上 production
    huijiewei
        26
    huijiewei  
       2016-09-07 12:39:56 +08:00
    也就是说可以考虑替换掉 nginx 了。

    这种恶性的 bug 竟然不在 stable 版本修复
    josephus
        27
    josephus  
       2017-07-12 21:58:08 +08:00
    @huijiewei
    NGINX 如此稳定高性能,又如此年轻有活力。
    如今哪个公司没使用?搞笑吧
    关于   ·   帮助文档   ·   博客   ·   API   ·   FAQ   ·   实用小工具   ·   1097 人在线   最高记录 6679   ·     Select Language
    创意工作者们的社区
    World is powered by solitude
    VERSION: 3.9.8.5 · 24ms · UTC 18:23 · PVG 02:23 · LAX 10:23 · JFK 13:23
    Developed with CodeLauncher
    ♥ Do have faith in what you're doing.