背景

我们这边网关服务使用的 kong,前段时间上线一个服务,这个服务它报错了,产生了502的错误码,追查这个报错的时候发现了网关服务的两个可疑的地方,第一个疑点是我们在Kong上配置的 Retries = 5,但是实际实际上我们的代理重试至多只会重试三次。第二个疑点是我们的重试只重试了502 和 504,大量的500错误没有重试。带着这两个问题了查了下kong和openresty代码。

结论

首先给出问题的结论

第一个问题 Kong上配置的 Retries = 5,但是实际上只会重试三次。出现这个问题的原因是因为我们在nginx上有一行配置

proxy_next_upstream_tries 3;

当我们在基于openresty Kong 上做 balancer.set_more_tries(5) 这个操作的时候nginx会基于保护措施启用nginx的配置 proxy_next_upstream_tries,所以proxy重试的时候最多只能重试三次。

第二个问题,就是为什么只有502 504 作出了重试,而且500没有做重试

这个的原因也是因为我们在nginx的配置里面有这么一行配置

proxy_next_upstream error timeout http_502 http_504 non_idempotent;

只需要加上http_500 500的错误码就可以重试了。

问题的定位

先说一下第一个问题的定位过程

主要是不知道有 nginx 有proxy_next_upstream_tries 这个参数,一直以为是openresty balancer.set_more_tries 控制的重试次数,一度自以为是的觉得这是bug,都想提个issues,直到在openresty的群组邮件里面春哥有一个关于这个问题的回复。

这个问题春哥在openresty的邮件群组里作出过解释

Hello!

2015-11-19 18:52 GMT+08:00 DeJiang Zhu:
>> > - 在 `proxy_next_upstream_tries 0;` 的时候, set_more_tries 好像没有效果了.
>
> 我测试了也是这样
> 然后看了代码发现: set_more_tries 并不能超过 proxy_next_upstream_tries 的配置 [1] 这是故意的,proxy_next_upstream_tries 规定的是重试上限。这可以避免 Lua 代码逻辑上的错误而导致无休止的重试。 Regards,
-agentzh

就看到了 proxy_next_upstream_tries 配置,以及互斥的时候以哪个为准。

第二个问题,上游500的错误码没有被重试。

这个问题的定位主要是陷入了以前引入Kong的一个误区了,我们的服务引入Kong的其中一个原因就是有些服务重启中发生错误的不能将服务重试到没有问题的上游服务器上去(其实主要是nginx不能按照我们的预想重试到上游服务上)。所以一直以为这是Kong的问题,所以把Kong的Kong init中关于Kong.balancer()的方法看了很长时间,测试了好多次,才确定不是这里问题,后来又去看了下 Passive health checks 被动健康检查代码,以为是这里做了重试,上游服务区的列表轮训引起的,最后也确定了跟这里没有关系。

最后一个一个过proxy_XXX的方法的时候,发现了 proxy_next_upstream 的配置说明,这个函数其实手册将的特别清楚

http://nginx.org/en/docs/http/ngx_http_proxy_module.html#proxy_next_upstream

Specifies in which cases a request should be passed to the next server:

error
an error occurred while establishing a connection with the server, passing a request to it, or reading the response header;
timeout
a timeout has occurred while establishing a connection with the server, passing a request to it, or reading the response header;
invalid_header
a server returned an empty or invalid response;
http_500
a server returned a response with the code 500;
http_502
a server returned a response with the code 502;
....
non_idempotent
normally, requests with a non-idempotent method (POST, LOCK, PATCH) are not passed to the next server if a request has been sent to an upstream server (1.9.13); enabling this option explicitly allows retrying such requests;

其它参数挺简单的,有哪些请求应该被转发到下一个上游服务器。主要是最后一个参数

non_idempotent, 默认情况下一些非幂等的函数(POST, LOCK, PATCH)不会被转发到下一个上游服务器,这个参数会允许此类请求也被转发到下一个上游服务器上。

还是应该多研究书册,仔细看说明

nginx proxy_next_upstream 与openresty balancer.set_more_tries的使用的更多相关文章

  1. Nginx插件之openresty反向代理和日志滚动配置案例

    Nginx插件之openresty反向代理和日志滚动配置案例 作者:尹正杰 版权声明:原创作品,谢绝转载!否则将追究法律责任. 一.openresty介绍 1>.Nginx介绍 Nginx是一款 ...

  2. 接入层高性能缓存技术nginx+redis利器OpenResty

    一. OpenRestyOpenResty是一个基于 Nginx与 Lua的高性能 Web平台,其内部集成了大量精良的 Lua库.第三方模块以及大多数的依赖项.用于方便地搭建能够处理超高并发.扩展性极 ...

  3. 关于nginx proxy_next_upstream 重试 和 max_fails的那些事

    背景及简要分析 前几天一次故障定位的时候发现,后端服务(java)在从故障中恢复之后,会出现大量499,且会持续较长时间无法自行恢复.根本原因是服务容量问题,处理太慢导致客户端等不了了,主动断开.不过 ...

  4. 使用SkyWalking监控nginx (以openresty为例)

    安装使用SkyWalking先看这篇文章,地址:https://www.cnblogs.com/sanduzxcvbnm/p/15829781.html 使用SkyWalking监控nginx借助的是 ...

  5. Nginx+lua+openresty精简系列

    1. CentOS系统安装openresty 你可以在你的 CentOS 系统中添加 openresty 仓库,这样就可以便于未来安装或更新我们的软件包(通过 yum update 命令).运行下面的 ...

  6. OpenResty(nginx+lua) 入门

    OpenResty 官网:http://openresty.org/ OpenResty 是一个nginx和它的各种三方模块的一个打包而成的软件平台.最重要的一点是它将lua/luajit打包了进来, ...

  7. openresty nginx 安装过程记录

    转载请注明原始地址 http://www.cnblogs.com/dongxiao-yang/p/4877799.html 一 :系统版本 1 cat /etc/issue: CentOS relea ...

  8. (转)OpenResty(nginx+lua) 开发入门

    原文:https://blog.csdn.net/enweitech/article/details/78519398 OpenResty 官网:http://openresty.org/  Open ...

  9. OpenResty全功能Web应用服务器,打包了标准的 nginx 核心

    OpenResty打包了标准的 nginx 核心,很多的常用的第三方模块,以及它们的大多数依赖项. 通过揉和众多设计良好的 nginx 模块,OpenResty 有效地把 nginx 服务器转变为一个 ...

随机推荐

  1. ant的copy标签使用方法

    对于ant里拷贝用的标签的用法,此文(来自 http://electiger.blog.51cto.com/112940/39575 )讲得很好,注意其中黑体字部分,今天被这个问题耽误了20分钟. A ...

  2. 解析java源文件

    尝试从java源文件中解析出类.方法.属性等信息,但下面的代码没有完全实现. Sub parseJava() Dim package_name as String 'read a file Docum ...

  3. 安鸾CTF Writeup SSRF03

    SSRF03 题目URL: http://whalwl.host:2000/ 其中的弯路我就不多说了,直接上解题思路 方法和SSRF02类似都是找内网机器端口,继续用ssrf02 这道题的方法:htt ...

  4. Qt多窗口编程详解

    常用的窗体基类是 QWidget.QDialog 和 QMainWindow,在创建 GUI 应用程序时选择窗体基类就是从这 3 个类中选择. QWidget 直接继承于 QObject,是 QDia ...

  5. 二级C语言题集

    时间:2015-5-13 18:01 在131题之后是按考点分类的题集,有需要的朋友可以看一下 ---------------------------------------------------- ...

  6. HTTP系列之:HTTP缓存

    目录 简介 HTTP中的缓存种类 HTTP中缓存响应的状态 HTTP中的缓存控制 缓存刷新 revving 缓存校验 Vary响应 总结 简介 为了提高网站的访问速度和效率,我们需要设计各种各样的缓存 ...

  7. SpringMVC笔记(3)

    一.SpringMVC 拦截器 1.1 快速入门 步骤 创建拦截器类实现HandlerInterceptor接口 public class MyInterceptor01 implements Han ...

  8. Qt5获取系统文件图标,文件路径

    获取系统图标: QFileIconProvider icon_provider; QIcon icon = icon_provider.icon(QFileIconProvider::Folder); ...

  9. vue 接入 vod-js-sdk-v6.js 完成视频上传

    东西有点多,耐心看完.按照操作一步一步来,绝对能成功 首先:npm 引入 npm install vod-js-sdk-v6 mian.js  全局引入  //腾讯云点播 import TcVod f ...

  10. Python - 面向对象编程 - super()

    前置知识 继承的详解:https://www.cnblogs.com/poloyy/p/15216652.html 子类方法的重写:https://www.cnblogs.com/poloyy/p/1 ...