游客发表
凌晨三点,负载服务某电商平台的均衡运维群里跳出一条告警:订单服务响应时间从80毫秒飙到2.3秒。值班工程师扫了一眼监控图,负载服务发现三台应用服务器里有一台的均衡CPU直接拉满,另外两台却闲得发慌。负载服务问题不在代码,均衡也不在数据库——流量全砸到那台过载的负载服务机器上了。负载均衡器没起作用。均衡
这事听起来低级,负载服务但真不少见。均衡很多人以为在架构图里画个负载均衡器就万事大吉,负载服务实际上它更像一个交通警察,均衡手里拿着对讲机,负载服务得知道哪条路堵了、均衡哪条路空着。负载服务如果它只按轮询的方式机械地分发请求,完全不看后端服务器的真实状态,那跟随机指路没什么区别。
负载均衡服务器干的事,说白了就两件:选谁和怎么转。
选谁,靠的是调度算法。轮询最简单,请求挨个分,适合后端机器配置完全一致、请求耗时也差不多的场景。但现实往往不是这样。有的请求查缓存,5毫秒就返回;有的请求要跑复杂报表,得花3秒。这时候轮询就坑了——前面那台机器可能已经堆了上百个慢请求,轮询算法还傻乎乎地往它身上派活。加权轮询稍微聪明点,给配置高的机器多分一些,但权重是静态的,它不知道某台机器此刻是不是正在GC停顿。
最小连接数算法更贴近实际。它看的是每台后端服务器当前有多少个活跃连接,谁少就给谁。这招在请求耗时差异大的场景下效果明显。我见过一个视频转码服务,把调度算法从轮询换成最小连接数之后,整体吞吐量直接涨了40%。原因很简单:转码任务耗时从几秒到几分钟不等,轮询会让某台机器积压大量长任务,而最小连接数能动态避开这些“重灾区”。
怎么转,涉及的是转发模式。四层负载均衡(比如LVS)只看IP和端口,不改数据包内容,转发效率极高,一台普通服务器能扛几十万并发连接。但它有个硬伤:它不知道HTTP请求里带的是啥。七层负载均衡(比如Nginx、HAProxy)会把请求完整拆开,能看到URL、Cookie、Header,于是可以做更精细的调度——把图片请求发给图片缓存集群,把API请求发给应用服务器集群。代价是性能开销更大,不过现代CPU跑Nginx,单机几万QPS问题不大。
健康检查是另一个容易被忽视的细节。默认配置往往只检查TCP端口通不通,端口开着就认为服务正常。可实际场景里,应用进程还在、端口还听着,但内部线程池已经耗尽,所有请求都超时。这时候TCP检查依然显示“健康”,负载均衡器继续往这台“僵尸”机器上送流量。更靠谱的做法是检查一个专门的健康接口,这个接口要能反映应用的真实状态——数据库连接池是否可用、依赖的下游服务是否超时、队列是否积压。
还有个坑是会话保持。电商购物车、用户登录态这些场景,如果同一个用户的请求被分到不同后端服务器,而会话数据又没有集中存储,用户就会发现自己一会儿登录着一会儿又掉线了。解决办法要么是把会话数据抽到Redis里,让后端服务器无状态化;要么在负载均衡器上配置基于Cookie的会话保持。前者更彻底,后者更省事,看团队怎么权衡。
我个人的判断是:负载均衡不是配完就完事的静态组件。它需要根据业务特征选算法,根据故障模式调健康检查,根据流量变化做动态扩缩容。把它当成一个只会转发流量的“死”设备,迟早会在某个凌晨三点收到那条你不想看到的告警。
友情链接