SpringCloud学习——服务调用与负载均衡(Ribbon、OpenFeign)
Ribbon
Spring Cloud Ribbon 是一套基于 Netflix Ribbon 实现的客户端负载均衡和服务调用工具。
Ribbon 会从服务注册中心(如 Eureka Server)中获取服务端列表,然后通过某种负载均衡策略(如简单轮询、随机连接等)将请求分摊给多个服务提供者,从而达到负载均衡的目的。
依赖:由于
spring-cloud-starter-netflix-eureka-client
已经包含spring-cloud-starter-netfilx-ribbon
,故而无需额外添加依赖。
负载均衡
负载均衡(Load Balance) ,简单点说就是将用户的请求平摊分配到多个服务器上运行,以达到扩展服务器带宽、增强数据处理能力、增加吞吐量、提高网络的可用性和灵活性的目的。常见的负载均衡方式有两种:
- 服务端负载均衡
- 客户端负载均衡
服务端负载均衡/集中式负载均衡
服务端负载均衡是在客户端和服务端之间建立一个独立的负载均衡服务器,该服务器既可以是硬件设备(例如 F5),也可以是软件(例如 Nginx)。这个负载均衡服务器维护了一份可用服务端清单,然后通过心跳机制来删除故障的服务端节点,以保证清单中的所有服务节点都是可以正常访问的。
当客户端发送请求时,该请求不会直接发送到服务端进行处理,而是全部交给负载均衡服务器,由负载均衡服务器按照某种算法(例如轮询、随机等),从其维护的可用服务清单中选择一个服务端,然后进行转发。
服务端负载均衡具有以下特点:
- 需要建立一个独立的负载均衡服务器。
- 负载均衡是在客户端发送请求后进行的,因此客户端并不知道到底是哪个服务端提供的服务。
- 可用服务端清单存储在负载均衡服务器上。
客户端负载均衡
客户端负载均衡是将负载均衡逻辑以代码的形式封装到客户端上,即负载均衡器位于客户端。客户端通过服务注册中心(例如 Eureka Server)获取到一份服务端提供的可用服务清单。有了服务清单后,负载均衡器会在客户端发送请求前通过负载均衡算法选择一个服务端实例再进行访问,以达到负载均衡的目的。
客户端负载均衡具有以下特点:
- 负载均衡器位于客户端,不需要单独搭建一个负载均衡服务器。
- 负载均衡是在客户端发送请求前进行的,因此客户端清楚地知道是哪个服务端提供的服务。
- 客户端都维护了一份可用服务清单,而这份清单都是从服务注册中心获取的。
Ribbon 就是一个基于 HTTP 和 TCP 的客户端负载均衡器,当我们将 Ribbon 和 Eureka 一起使用时,Ribbon 会从 Eureka Server(服务注册中心)中获取服务端列表,然后通过负载均衡策略将请求分摊给多个服务提供者,从而达到负载均衡的目的。
Ribbon 可以与 RestTemplate 配合使用,以实现微服务之间的调用。RestTemplate 是 Spring 家族中的一个用于消费第三方 REST 服务的请求框架。RestTemplate 实现了对 HTTP 请求的封装,提供了一套模板化的服务调用方法。通过它,Spring 应用可以很方便地对各种类型的 HTTP 请求进行访问。
Ribbon客户端负载均衡与Nginx服务端负载均衡区别
- Nginx 是服务器负载均衡,客户端所有请求都会交给 Nginx ,然后由 Nginx 实现转发请求。即负载均衡是由服务端实现的。
- Ribbon 是客户端负载均衡,在调用微服务接口时候,会在注册中心上获取注册信息服务列表,获取之后缓存到 JVM 本地,从而在本地实现 RPC 远程服务调用技术。即在客户端实现负载均衡。
内置负载均衡规则
负载均衡规则是 Ribbon 的核心,下面来看一下 Ribbon 内置的负载均衡规则。
- RoundRobinRule:轮询,轮询index,选择index对应位置的Server;
- RandomRule:随机
- RetryRule:先按照RoundRobinRule的策略获取服务,如果获取服务失败则在指定时间内会进行重试
- WeightedResponseTimeRule:对RoundRobinRule的扩展,响应速度越快的实例选择权重越大,越容易被选择
- BestAvailableRule:会先过滤掉由于多次访问故障而处于断路器跳闸状态的服务,然后选择一个并发量最小的服务
- AvailabilityFilteringRule:先过滤掉故障实例,再选择并发较小的实例
- ZoneAvoidanceRule:默认规则,复合判断server所在区域的性能和server的可用性选择服务器
OpenFeign
Feign 对 Eureka、Ribbon 及 Hystrix 进行了集成,利用 Ribbon 维护了一份可用服务清单,并通过 Ribbon 实现了客户端的负载均衡,借助 Hystrix 完成服务降级、熔断、超时控制等。
Feign 是一种声明式服务调用组件,它在 RestTemplate 的基础上做了进一步的封装。通过 Feign,我们只需要声明一个接口并通过注解进行简单的配置(类似于 Dao 接口上面的 Mapper 注解一样)即可实现对 HTTP 接口的绑定。
OpenFeign 是 Spring Cloud 对 Feign 的二次封装,它具有 Feign 的所有功能,并在 Feign 的基础上增加了对 Spring MVC 注解的支持,例如 @RequestMapping、@GetMapping 和 @PostMapping 等。
服务调用
新增依赖
1 | <!--openfeign--> |
application.yml(无需添加新的配置信息)
1 | server: |
主启动类激活 @EnableFeignClients
1 |
|
业务逻辑接口上使用 @FeignClient
配置调用 provider 服务,接口路径与 provider 服务的 Controller 接口路径一致。
1 |
|
Controller 接口,无需再手动通过 RestTemplate 进行 HTTP 调用,而是通过 service 接口调用,符合习惯。
1 |
|
Feign 自带负载均衡配置项,集成了 Ribbon。
超时控制
application.yml
1 | #设置feign客户端超时时间(OpenFeign默认支持ribbon)(单位:毫秒) |
日志增强
Feign提供了日志打印功能,我们可以通过配置来调整日志级别,从而了解Feign 中 Http请求的细节。
说白了就是对Feign接口的调用情况进行监控和输出。
日志级别
- NONE:默认的,不显示任何日志;
- BASIC:仅记录请求方法、URL、响应状态码及执行时间;
- HEADERS:除了BASIC中定义的信息之外,还有请求和响应的头信息;
- FULL:除了HEADERS中定义的信息之外,还有请求和响应的正文及元数据。
新增配置类
1 |
|
修改 yml 配置文件
1 | logging: |