线上Nginx频繁502的排查过程与解决方案

 更新时间:2026年01月27日 09:53:44   作者:白露与泡影  
本文详细介绍了在线上Nginx频繁出现502错误的排查过程,包括监控数据、Nginx和后端服务的状态检查、连接数分析以及最终的解决方案,作者通过调整系统参数、优化Nginx配置和多实例负载均衡等措施,成功解决了502错误问题,需要的朋友可以参考下

监控告警:Nginx 502错误率飙升到5%。

看了眼后端服务,运行正常,没有报错。重启Nginx,好了一会又开始502。

排查了3个小时,最后发现是upstream配置的问题。记录一下排查过程。

问题现象

监控数据

  • 502错误率:从0.1% → 5%
  • 后端服务:正常运行,无报错
  • CPU/内存:正常
  • 发生时间:流量高峰期

特点

  • 不是全部请求都502,大部分正常
  • 重启Nginx后短暂恢复,然后又出现
  • 后端服务日志没有异常

排查过程

Step 1:看Nginx错误日志

tail -f /var/log/nginx/error.log

发现大量这样的错误:

upstream timed out (110: Connection timed out) while connecting to upstream
upstream prematurely closed connection while reading response header

关键信息:是upstream连接的问题,不是后端服务本身的问题。

Step 2:检查后端服务状态

# 查看后端服务进程
ps aux | grep java

# 查看端口监听
ss -tlnp | grep 8080

# 直接测试后端
curl -I http://127.0.0.1:8080/health

后端服务正常,直接访问返回200。

Step 3:检查连接数

# 查看Nginx到后端的连接数
ss -ant | grep 8080 | wc -l

# 查看连接状态分布
ss -ant | grep 8080 | awk '{print $1}' | sort | uniq -c

发现问题了:

850 ESTABLISHED
   120 TIME_WAIT
    50 SYN_SENT

有50个连接卡在SYN_SENT状态,说明Nginx到后端的新连接建立不上。

Step 4:检查后端连接队列

# 查看后端服务的accept队列 
ss -lnt | grep 8080

输出:

State    Recv-Q   Send-Q   Local Address:Port
LISTEN   129      128      0.0.0.0:8080

问题找到了! Recv-Q是129,Send-Q是128。

这说明accept队列满了(128是默认值),新连接无法被接受。

根因分析

什么是accept队列

客户端 → SYN → 服务端(半连接队列)
服务端 → SYN+ACK → 客户端
客户端 → ACK → 服务端(全连接队列/accept队列)
应用程序 accept() → 取出连接

当accept队列满了,新的完成三次握手的连接无法进入队列,客户端会收到超时或RST。

为什么队列满了

后端是Spring Boot应用,默认配置:

server:
  tomcat:
    accept-count: 100  # Tomcat的accept队列

而系统层面的限制是net.core.somaxconn = 128,取两者较小值,所以实际accept队列只有128。

流量高峰时

  1. 请求量大,新连接多
  2. accept队列128不够用
  3. 新连接被拒绝
  4. Nginx收到超时,返回502

解决方案

方案一:调大系统参数

# 查看当前值
sysctl net.core.somaxconn

# 临时修改
sysctl -w net.core.somaxconn=65535

# 永久修改
echo "net.core.somaxconn = 65535" >> /etc/sysctl.conf
sysctl -p

方案二:调整Tomcat配置

server:
  tomcat:
    accept-count: 1000      # accept队列大小
    max-connections: 10000  # 最大连接数
    threads:
      max: 500              # 最大工作线程数

方案三:Nginx upstream优化

upstream backend {
    server 127.0.0.1:8080 max_fails=3 fail_timeout=30s;
    
    keepalive 100;  # 保持连接数,减少新建连接
}

server {
    location / {
        proxy_pass http://backend;
        
        proxy_connect_timeout 5s;      # 连接超时
        proxy_read_timeout 60s;        # 读取超时
        proxy_send_timeout 60s;        # 发送超时
        
        proxy_http_version 1.1;        # 使用HTTP/1.1
        proxy_set_header Connection ""; # 配合keepalive
    }
}

方案四:多实例负载均衡

如果单实例撑不住,可以部署多实例:

upstream backend {
    least_conn;  # 最少连接数策略
    
    server 127.0.0.1:8080 weight=1;
    server 127.0.0.1:8081 weight=1;
    server 127.0.0.1:8082 weight=1;
    
    keepalive 100;
}

最终配置

系统参数(/etc/sysctl.conf):

net.core.somaxconn = 65535
net.ipv4.tcp_max_syn_backlog = 65535
net.core.netdev_max_backlog = 65535

Spring Boot配置

server:
  tomcat:
    accept-count: 2000
    max-connections: 20000
    threads:
      max: 500
      min-spare: 50

Nginx配置

upstream backend {
    server 127.0.0.1:8080;
    keepalive 200;
}

server {
    location / {
        proxy_pass http://backend;
        proxy_http_version 1.1;
        proxy_set_header Connection "";
        proxy_connect_timeout 5s;
        proxy_read_timeout 60s;
    }
}

优化效果

指标优化前优化后
502错误率5%0.01%
accept队列溢出频繁
连接建立时间不稳定稳定<5ms

排查命令汇总

# 查看Nginx错误日志
tail -f /var/log/nginx/error.log

# 查看连接状态
ss -ant | grep <端口>

# 查看监听队列
ss -lnt | grep <端口>

# 查看队列溢出统计
netstat -s | grep -i listen

# 查看系统参数
sysctl net.core.somaxconn

# 实时监控连接数
watch -n 1 'ss -ant | grep <端口> | wc -l'

经验总结

502原因排查方向
upstream timed out后端处理慢或连接队列满
connection refused后端服务没启动
no live upstreams所有后端都不可用
prematurely closed后端主动断开连接

这次的坑:后端服务看起来正常,但accept队列满了,新连接进不来。

教训

  1. 系统默认的somaxconn=128太小,生产环境必须调大
  2. Nginx配置keepalive可以减少新建连接,降低队列压力
  3. 监控要加上连接队列指标

以上就是线上Nginx频繁502的排查过程与解决方案的详细内容,更多关于线上Nginx频繁502排查的资料请关注脚本之家其它相关文章!

相关文章

  • Nginx 路由转发和反向代理location配置实现

    Nginx 路由转发和反向代理location配置实现

    本文主要介绍了Nginx 路由转发和反向代理location配置实现,文中通过示例代码介绍的非常详细,具有一定的参考价值,感兴趣的小伙伴们可以参考一下
    2021-11-11
  • Nginx通过用户IP获取所在国家及地理位置的实现方法

    Nginx通过用户IP获取所在国家及地理位置的实现方法

    Nginx是一款高性能、轻量级的Web服务器和反向代理服务器,今天讲解Nginx十分常用的功能之一,通过IP获取用户所在的国家,一般广泛应用在各类需要定位的网站上面,来定位用户首次访问的国家,通过IP解析库GeoLite2-Country来实现功能,需要的朋友可以参考下
    2023-10-10
  • 深度解析Nginx日志分析与499状态码问题解决

    深度解析Nginx日志分析与499状态码问题解决

    在Web服务器运维和性能优化过程中,Nginx日志是排查问题的重要依据,本文将围绕Nginx日志分析、499状态码的成因、排查方法及解决方案展开讨论,并结合实际案例提供优化建议
    2025-07-07
  • Nginx如何提高Web应用的性能和安全性

    Nginx如何提高Web应用的性能和安全性

    现在越来越多的应用都离不开Web应用,但Web应用的性能问题也越来越成为企业关注的焦点,而Nginx作为一款高性能的Web服务器和反向代理服务器,能够为企业带来很多优势,Nginx的应用场景非常广泛,对于Web应用的优化、安全性的提升有着非常重要的作用
    2023-11-11
  • Nginx proxy_pass如何到https后端

    Nginx proxy_pass如何到https后端

    这篇文章主要介绍了Nginx proxy_pass如何到https后端问题,具有很好的参考价值,希望对大家有所帮助,如有错误或未考虑完全的地方,望不吝赐教
    2024-05-05
  • Nginx rewrite和proxy_pass的区别及说明

    Nginx rewrite和proxy_pass的区别及说明

    这篇文章主要介绍了Nginx rewrite和proxy_pass的区别及说明,具有很好的参考价值,希望对大家有所帮助,如有错误或未考虑完全的地方,望不吝赐教
    2024-06-06
  • Nginx伪静态配置和常用Rewrite伪静态规则集锦

    Nginx伪静态配置和常用Rewrite伪静态规则集锦

    伪静态是一种可以把文件后缀改成任何可能的一种方法,如果我想把php文件伪静态成html文件,这种相当简单的,下面我来介绍nginx 伪静态配置方法有需要了解的朋友可参考。
    2014-06-06
  • Nginx实现404页面的几种方法(三种)

    Nginx实现404页面的几种方法(三种)

    一个网站项目,肯定是避免不了404页面的,通常使用Nginx作为Web服务器时,有些相关配置方法,下面小编给大家带来了Nginx实现404页面的几种方法,感兴趣的朋友一起看看吧
    2018-08-08
  • Nginx监控模块(vts模块)详解

    Nginx监控模块(vts模块)详解

    国内用Nginx的比较多,下面这篇文章主要给大家介绍了关于Nginx监控模块(vts模块)的相关资料,文中通过实例代码介绍的非常详细,需要的朋友可以参考下
    2022-09-09
  • 使用Nginx搭建图片服务器(windows环境下)

    使用Nginx搭建图片服务器(windows环境下)

    这篇文章主要介绍了使用Nginx搭建图片服务器(windows环境下),小编觉得挺不错的,现在分享给大家,也给大家做个参考。一起跟随小编过来看看吧
    2018-06-06

最新评论