Skip to content

概念卡片:客户端负载均衡 Ribbon

一句话机制:负载均衡分两种——服务端负载均衡(独立 LB 服务器,如 Nginx/F5,转发请求)和客户端负载均衡(负载均衡逻辑在客户端,如 Ribbon,本地选实例再发请求);Ribbon 是 Spring Cloud 的客户端负载均衡组件,配合注册中心拿到服务清单,按算法选一个实例调用。

服务端 vs 客户端负载均衡

维度服务端 LB客户端 LB(Ribbon)
位置独立 LB 服务器(Nginx/F5)负载均衡器在客户端
选实例时机请求到达 LB 后转发客户端发请求前自己选
服务清单存在 LB 服务器客户端从注册中心拉取
客户端感知不知道谁提供服务明确知道选中的实例
额外部署要建 LB 服务器无需独立部署

关键机制:@LoadBalanced

java
@Bean
@LoadBalanced                       // 给 RestTemplate 加负载均衡能力
public RestTemplate restTemplate() {
    return new RestTemplate();
}

// 调用时用服务名,Ribbon 自动解析成具体实例地址
restTemplate.getForObject("http://service-name/api/xxx", String.class);

@LoadBalanced 的原理:拦截 RestTemplate 请求,把「服务名」替换成「负载均衡选出的实例 IP:端口」。

常用负载均衡策略

策略说明
轮询 RoundRobin依次轮询,默认
随机 Random随机选一个
加权响应时间响应快的实例权重高
最小并发选并发最少的实例

不变量(必须成立的约束)

  • Ribbon 是客户端负载均衡,需要配合注册中心(拉服务清单)才能工作。
  • 调用方用服务名(不是 IP),由 Ribbon 在发请求前解析成具体实例。
  • OpenFeign 底层也是 Ribbon(现已演进为 Spring Cloud LoadBalancer)做负载均衡。

踩坑案例

  • 现象RestTemplate 用服务名调用报「UnknownHostException」。 原因:忘了加 @LoadBalanced,服务名没被解析成实例。解决:Bean 上加 @LoadBalanced

常见误解

  • 以为负载均衡都是 Nginx 那种服务端 LB → Ribbon 是客户端 LB,逻辑在调用方本地。
  • 以为 Ribbon 还活跃维护 → 已进入维护模式,Spring Cloud 新版本用 LoadBalancer 替代(概念相通)。

关联

  • Dubbo 的软负载均衡:[概念卡片:Dubbo RPC框架](./概念卡片:Dubbo RPC框架)
  • 微服务总览:微服务技术栈总览
  • 源:B40-资源/语雀-Code-Summary/Middleware/Limit&Balance/BalanceRibbon(3 篇)
最近更新