资讯动态

从Nginx到NLB:高并发架构下的四层负载均衡实战

发布时间:2026/9/11 3:01:08 来源:尧图企业网站定制
刚接手一个千万级日活的项目时我也以为Nginx能扛下所有。后来才发现当流量真到了天花板的门槛上光靠七层转发和一堆调优参数根本不够用。那时候我接触到了NLB网络型负载均衡才算是撕开了高性能流量分发的一道口子——单实例转发性能动不动就上亿并发这个数字起初我是不信的直到自己压测后才发现原来问题从来不在于设备性能而在于架构设计时就该把负载均衡的层级分清楚。NLB能做什么简单说它在四层网络层面就把流量分发干完了不碰数据包里的业务内容转发效率比七层的Nginx高出一个量级。它适合谁适合被高并发折磨的架构师、运维工程师也适合正在设计大规模分布式系统的开发人员。如果你还在靠多台Nginx堆性能和Keepalived抢主备这篇文章值得看完——聊的不仅仅是NLB怎么用还包括这背后“等开销负载均衡”的架构思路以及它对存量Nginx负载均衡方案的一次降维打击。1. 方案选型为什么亿级并发场景下要选NLB而不是硬扛Nginx或F5做流量入口选型没有标准答案只有适合不适用的区别。先把结论放这儿高并发场景第一层入口用NLB业务流量精细化管控再用Nginx这套组合基本可以覆盖90%以上的大流量架构需求。1.1 四层转发和七层转发性能差距到底差在哪传统用Nginx做负载均衡本质是七层转发。客户端发来一个HTTP请求Nginx要把整个请求解析出来——读到HTTP头、解析URL、按location匹配规则、再把请求转发给后端。每一步都有CPU计算参与解析越深消耗越大。NLB是四层转发工作在传输层。它不关心来的包是HTTP还是MySQL协议只管按IP和端口把数据包转发出去。转发路径短、状态少、纯内核态完成单位时间内能处理的包数量自然高出一个数量级。我拿自己的压测数据做个参照。单台8核Nginx服务开启epoll和keepalive优化后常规HTTP请求能扛到五六万QPS这已经算调得比较好了。而用NLB后底层单实例的PPS每秒转发包数能达到千万级别换算成并发连接数就是百万到千万级够好几个Nginx集群才能追上的量。这不是说Nginx没用而是定位错了。把Nginx放在最前面对抗所有流量洪峰就相当于让一个精通业务逻辑的客服去干保安的活。NLB干保安Nginx干客服各司其职才是正经架构。1.2 从F5到云上NLB硬件设备为什么在逐步让位十年前大流量入口第一选择往往是F5这类硬件负载均衡设备。性能确实强单台设备百万级并发不在话下但问题也明显——贵一台设备动辄几十万甚至百万起步扩容周期长流量涨了要采购、上架、调试一周算快的还得养懂硬件网络的人来维护。云上NLB天然解决了这三个问题。它没有实体设备是虚拟化出来的负载均衡服务底层跑在分布式的转发集群上。流量涨了可以自动扩展或者一键升配不需要采购硬件可用性由服务商的多可用区机制保障不再依赖单台物理设备。我在生产环境迁移过一次大流量入口之前是F5做主备看了不少监控指标和网络拓扑维护成本一直不低。后来切到NLB后整个入口的管理变得很轻——创建实例、配监听器、挂后端服务器组三个步骤搞定F5上那些网络ACL、IRule规则完全靠边站了。省下来的不仅仅是预算更重要的是运维复杂度和响应速度的改善。等开销负载均衡这个热门概念在NLB上的体现就是“每个转发节点做的事情是一样多的”。没有主备之分没有空闲等待的节点每个实例都在真实处理流量这意味着整体吞吐量可以随着节点横向扩展而线性增长——传统主备架构根本做不到这一点。2. 核心机制解构NLB高性能背后的几个关键设计说NLB性能好不是凭空吹出来的背后有几个核心技术点支撑。理解了这些你在做容量评估和问题排查时会更有底。2.1 内核态转发 数据面加速NLB底层采用内核态数据转发数据包从网卡进来后不再经过用户态协议栈而是在内核协议栈内直接完成匹配和转发。省去了内核态和用户态之间的数据拷贝也省去了系统调用的开销。举个不精确但容易理解的类比普通转发是文件在两个人之间传递每次都要放到桌面再让对方拿内核态转发是两个人直接手递手中间少了一道流程。更底层的加速技术还包括DPDK数据平面开发套件它允许数据包绕过内核协议栈直接从网卡通过轮询模式送到用户态应用程序处理。常规中断模式下一个网卡每秒收到百万级数据包时CPU光处理中断就快饱和了DPDK改成轮询后CPU不再被动响应中断而是主动、持续地去收包吞吐率可以提升数倍。我手工在测试环境验证过NLB满负荷转发时CPU使用率能稳定维持在一个较低水位基本印证了它的数据面转发逻辑确实不依赖高CPU开销。这也是它能在高PPS场景下保持低延迟的核心原因。2.2 会话保持和一致性哈希——粘住用户的关键机制大流量场景下会话保持是不可回避的硬需求。用户登录状态存在后端某台服务器上如果第二次请求被转发到了另一台用户就被迫重新登录这种体验没法接受。NLB支持多种会话保持方式最常用的是基于源IP的一致性哈希。什么叫一致性哈希你可以想象成把后端服务器排成一个环每个请求来了按源IP做哈希计算计算出的结果落在环的哪个区域就把请求发给对应的服务器。只要后端服务器列表不变同一个源IP的请求永远会落在同一台后端上这就实现了会话保持。一致性哈希还有一个额外好处就是当后端服务器增减时不需要重新计算全部映射关系只有部分请求会受影响其他请求还保持原来的转发路径。这比普通的取模哈希扩展性好了太多——取模哈希一扩缩容会产生大面积重新映射导致会话大量失效后端压力也可能瞬间激增。如果你真要追求极致均匀的流量分发可以配合NLB的加权轮询策略一起看。基础场景用轮询就够了一致性哈希用于有会话保持需求的场景两者各司其职。2.3 健康检查机制——把故障节点自动踢下线NLB能自动感知后端服务器状态的靠的是健康检查。常见方式有TCP探测和HTTP探测两种。TCP探测逻辑很简单负载均衡节点定期向后端服务器的某个端口发起TCP连接连接成功就认为是健康的连续失败几次就自动摘除。HTTP探测会更精细一点不光检查端口连通性还发起真实的HTTP请求检查返回状态码。比如配置了期望响应码为200后端返回503就赶紧撤掉。这里有个容易踩的坑健康检查的探测源IP往往是负载均衡的网关地址如果后端服务器安全组或iptables规则把探测IP封了就会产生后端一切正常但NLB判定不健康的情况。我在一次排查中就遇到过业务进程活得好好的它就是被NLB摘除流量最后发现是安全组把探测网段给拦了。健康检查参数也值得注意。间隔时间默认几秒到十几秒超时时间决定了多快判定失败不健康阈值和健康阈值分别决定了摘除和恢复的速度。生产环境我习惯把探测间隔设短一些比如5秒超时设3秒连续失败3次摘除——这样后端出问题时NLB最快15秒内就能把异常节点踢掉避免把请求打到故障机上。3. 实操上手从零搭建NLB入口处理一次完整的流量分发配置理论聊完直接进入实操。这部分以主流公有云的NLB产品为例流程大同小异但细节差异可能导致你磕磕绊绊建议跟着步骤走一遍。3.1 部署架构规划和网络规划动手创建NLB之前先把架构图画清楚。我建议的典型部署模式长这样客户端流量 → DNS解析到NLB公网IP → NLB监听器 → 后端服务器组多可用区部署的云服务器/容器后端服务器组前挂安全组只放行NLB所在网段的流量后端服务器组内至少跨两个可用区部署避免单可用区故障网络规划上要提前规划好NLB所在子网。NLB实例会占用子网内的IP地址如果子网太小IP耗尽会导致扩容受限。一般来说建议预留一个掩码26位以上的独立子网给NLB使用既满足当前需求也留足扩展空间。另外NLB本身支持跨地域、跨VPC做后端挂载取决于具体云厂商实现。但跨地域转发毕竟多一跳公网或专线延迟和带宽成本都要算进去一般不建议这么玩除非业务对强一致性的需求超过了延迟容忍度。3.2 创建NLB实例和监听器的完整流程在控制台上创建NLB的流程大致如下进入负载均衡控制台选择“创建NLB”。确定实例的网络类型公网NLB还是私网NLB。如果边缘节点有公网入口需求就选公网如果只是内网服务发现和调用就用私网。选择所属VPC和子网。公网NLB会为实例分配公网IP私网NLB则只有内网IP。选择计费模式。按规格付费和按用量付费都可以大流量场景我更推荐按用量付费——流量波动大按规格付费可能会出现规格买小不够用、买大浪费钱的情况。创建完成后进入实例详情配置监听器。监听器的核心参数如下协议TCP/UDP/TLS。HTTP业务走TCP足够不需要选TLS证书卸载可以放到后端的Nginx或应用层去做。端口一般设80或443如果后端入口没有独立网关。如果是内部服务按服务实际端口来。调度算法根据会话保持需求选加权轮询或一致性哈希。没有会话保持需求的用加权轮询最均匀。空闲连接超时TCP长连接场景要适度调大。默认值有时候太小会导致一条连接被NLB断开而客户端和后端都不知情影响业务。监听器配置完之后下一步是后端服务器组。把后端云服务器的IP和端口添加进去设置权重默认100然后配置健康检查的参数。我实测常用的参数组合是探测协议TCP探测端口跟后端服务端口一致间隔5秒超时3秒不健康阈值3次健康阈值2次。这套配置能在最快15秒内摘除故障节点业务影响面最小。3.3 流量接入和验证方法监听器配好后需要做流量接入验证。最简单的方式是curl -I http://NLB-IP:监听端口/观察返回结果是否来自后端真实服务。如果后端是多台服务器可以在每台后端的响应头里加入自定义字段比如X-Server-ID: nginx-01这样你通过NLB访问时就能确认请求确实被分发到了预期后端。如果要验证更多细节可以用tcpdump抓包确认流量经过的路径是否符合预期。比如在NLB所在节点和后端服务器上分别抓同一会话的包对比五元组信息就能判断是否走了NLB转发以及是否有NAT转换。后端服务器的系统日志中也会记录实际接收请求的来源IP。如果NLB工作在转发模式后端默认可能看到的是NLB的内网IP无法拿到真实客户端IP。这时需要配置NLB的客户端IP透传功能通常通过TCP Option地址或Proxy Protocol然后在后端软件里解析。这一块是生产环境非常容易忽略的点特别是需要做用户级限流或审计日志时没有真实IP数据很多分析都做不了。3.4 扩展性和高可用配置NLB一个核心优势是弹性。但弹性不代表不用配置——你要告诉它你在什么条件下需要扩展。主要的扩展方式有两种性能保障型在新建实例时选择最大规格比如最大连接数1000万新建连接速率50万/秒适用于流量高峰可预期的场景。按量弹性依赖负载均衡集群的自动扩容能力适用于流量波动不可控的场景。高可用层面建议开启多可用区部署。NLB会将实例的节点自动分布在多个可用区当一个可用区发生故障流量自动切换到健康可用区的节点上。这个开关通常在创建实例时就要选择后期也可以修改但会涉及IP变化提前做好规划更稳妥。另外记得把DNS解析的TTL调小比如60秒万一要做入口切换或故障迁移DNS生效速度快业务影响时间能控制在分钟级。4. 常见问题与排查技巧实录NLB的排障比Nginx简单很多但依然有一些典型的坑我帮大家梳理一下排查思路。4.1 后端连接被重置客户端报Connection reset这个现象的最常见原因是NLB空闲连接超时时间设置太短。客户端和后端建立了一个TCP长连接但超过空闲超时后NLB悄悄把这个连接回收了。客户端继续往这条连接上发数据时发现连接已经没有状态触发RST重置。排查思路很简单在客户端抓包看RST包的来源IP是不是NLB节点IP。如果是说明是NLB主动断连。查看监听的空闲连接超时配置调大超时值。同时检查后端服务的keepalive设置确保后端不会先于NLB断开连接。我遇到过一个更隐蔽的情况后端服务设置了TCP keepalive时长120秒NLB空闲超时设了60秒本来够用但后端偶尔处理慢导致攒了一批短暂空闲连接超过60秒后NLB直接断开客户端重连后刷出一片报错。后来把NLB空闲超时调到300秒问题当天消失。4.2 后端明明正常NLB却判定不健康这个问题的排查路径我上面说过大概率是安全组或防火墙拦截了健康检查探测流量。常规排查顺序确认NLB的路由/探测网段看安全组入方向是否放行对应网段。登录后端服务器查看系统日志中有没有来自NLB探测IP的访问记录。临时关掉安全组放通全部流量仅测试环境看NLB是否恢复健康状态。能恢复就说明是安全组规则有问题。另一种可能后端配置了iptables规则只允许指定来源IP访问某些端口NLB的探测IP不在白名单内。这类规则通常在基线加固时配置排查时容易忽略。4.3 会话保持失效用户频繁掉登录态架构是NLB → Nginx → 后端应用NLB上配了一致性哈希的会话保持但用户还是频繁掉线。这种多半是会话保持作用层级不够。问题出在Nginx这一层。NLB按客户端源IP的一致性哈希把请求固定到一台Nginx但Nginx转发到后端时没有配置ip_hash或Session保持策略它默认轮询分发到多台后端应用。用户请求落在后端A下一次落在后端B后端之间没有同步Session登录态自然就丢了。解决方式确认会话保持的最终靠端是后端应用自己共享Session存储比如Redis还是需要层层负载均衡都保持会话。如果用NLB的会话保持 Nginx的ip_hash两层都固定到同一台后端就能保证会话不漂移。更推荐的现代方案后端应用把Session数据放到分布式缓存Redis中保证任何一台后端都能读取这样负载均衡层不需要做会话保持水平扩展性更好。4.4 后端获取不到真实客户端IPNLB转发模式下默认会替换源IP为NLB节点IP后端拿不到真实客户端IP。需要开启NLB的客户端IP透传。最常见的透传方式是Proxy Protocol。在NLB监听器开启Proxy Protocol后后端需要对应的解析能力Nginx的配置server { listen 80 proxy_protocol; set_real_ip_from 100.64.0.0/10; # NLB内网网段按实际修改 real_ip_header proxy_protocol; }解析完成后后端业务就能通过$remote_addr拿到真实IP了。如果后端是其他类型服务也基本上都有对应的Proxy Protocol解析库核心思路一致。还有一个注意点开启Proxy Protocol后后端程序处理网络连接时要能正确解析这部分协议头如果后端程序不支持可能会把Proxy Protocol的文本数据当成业务请求的一部分反而导致服务异常。改配置前先确认后端版本是否支持。常见现象可能原因排查建议Connection reset空闲连接超时过短调大NLB监听器空闲超时同步检查后端keepalive健康检查失败安全组/防火墙拦截放行NLB探测网段核对iptables规则会话频繁丢失Session存储未共享或层级混乱确认会话靠端或引入Redis统一存储后端没有真实IP未开启客户端IP透传开启Proxy Protocol后端配置解析性能达不到预期监听器参数或后端容量不足分端排查先看后端水位再看NLB指标5. 几个容易被忽略的设计细节分享三个我踩过之后才彻底想通的细节影响范围不大但每个都可能让你多熬夜两个晚上。第一NLB和后端之间的安全组规则不建议配成“放行所有来源”而是精确放行NLB所在子网网段。这样即使后端被其他VPC误探测也不会暴露服务。配合安全组的描述信息写好注释后来接手的人也不会一头雾水。第二大流量场景下不要只在控制台看总带宽和总连接数要拆到“新建连接速率”和“并发连接数”两个维度分别看。有的业务QPS不高但都是短连接新建连接速率很高PPS消耗大。有些业务连接数大但很稳定对并发连接数的容量要求高。不区分场景去评估容量很容易做错升配和扩容决策。第三NLB和后端服务之间的TCP参数要统一调优。比如TCP窗口、TCP keepalive参数、TIME_WAIT回收策略后端服务器的内核参数如果跟NLB侧差距太大转发链路会出现莫名其妙的延迟抖动。最直接的方法是让后端的内核TCP参数规范化——统一设置一个合理的基线值再配合监控观察。关于nginx负载均衡和f5负载均衡我用过的感受是Nginx灵活可操控性强适合做七层路由和灰度发布F5稳定但贵适合预算充足的传统企业而NLB的定位是纯性能入口不抢业务逻辑的活配合Nginx做六级分工才最合理。现在架构师聊等开销负载均衡本质上都围绕同一个话题让每一层只做自己最擅长的事。入口层就专心对抗流量冲击业务层就专心处理业务逻辑。NLB在最前面把大流量接住并均匀分发后面的Nginx才有体力去处理复杂的路由规则和服务发现。这种分层思路比单点硬撑要耐用得多。如果你正准备做新项目的入口设计我建议你先画清楚流量模型——每秒新建多少连接、峰值并发多少、单连接平均持续时间多长再来选型。数据摆出来之后NLB适不适合你的场景答案基本一目了然。

读完文章,也想定制专属网站?

尧图设计师 24 小时内与您沟通定制方案

免费获取报价