SpringCloud - 新版淘汰 Ribbon,在 OpenFeign 中整合 LoadBalancer 负载均衡

这篇具有很好参考价值的文章主要介绍了SpringCloud - 新版淘汰 Ribbon,在 OpenFeign 中整合 LoadBalancer 负载均衡。希望对大家有所帮助。如果存在错误或未考虑完全的地方,请大家不吝赐教,您也可以点击"举报违法"按钮提交疑问。

目录

一、LoadBalancer 负载均衡

1.1、前言

1.2、LoadBalancer 负载均衡底层实现原理

二、整合 OpenFeign + LoadBalancer

2.1、所需依赖

2.2、具体实现

 2.3、自定义负载均衡策略


一、LoadBalancer 负载均衡


1.1、前言

在 2020 年以前的 SpringCloud 采用 Ribbon 作为负载均衡,但是 2020 年之后,SpringCloud 吧 Ribbon 移除了,而是使用自己编写的 LoadBalancer 替代.

因此,如果在没有加入 LoadBalancer 依赖的情况下,使用 RestTemplate 或 OpenFeign 远程调用,就会报以下错误:

feign用的是ribbon还是loadbal,SpringCloud & Alibaba,负载均衡,java,spring boot

这就是在告诉你 LoadBalancing是未定义的(OpenFeign 中引入的依赖会使用 LoadBalancing),然后问你是不是忘记加入 spring-cloud-starter-loadbalancer 依赖.

1.2、LoadBalancer 负载均衡底层实现原理

a)在添加了 @LoadBalanced 注解之后,会启用拦截器对我们发起的服务调用请求进行拦截(注意,这里是针对我们发起的请求进行拦截),叫做 LoadBalancerInterceptor,它实现了 ClientHttpRequestInterceptor 接口:

@FunctionalInterface
public interface ClientHttpRequestInterceptor {
    ClientHttpResponse intercept(HttpRequest request, byte[] body, ClientHttpRequestExecution execution) throws IOException;
}

 intercept 方法如下:

public ClientHttpResponse intercept(final HttpRequest request, final byte[] body, final ClientHttpRequestExecution execution) throws IOException {
    URI originalUri = request.getURI();
    String serviceName = originalUri.getHost();
    Assert.state(serviceName != null, "Request URI does not contain a valid hostname: " + originalUri);
    return (ClientHttpResponse)this.loadBalancer.execute(serviceName, this.requestFactory.createRequest(request, body, execution));
}

主要就是这里的 intercept 方法拦截的请求.

b)这个拦截器具体做了什么事情呢,我们知道,被拦截的请求地址,并不是一个有效的主机地址,而是服务名称,因此需要通过 服务注册中心(Nacos)才能得到需要访问的主机地址.

loadBalancer.execute() 就是在获取请求对应的服务实例信息.

//从上面给进来了服务的名称和具体的请求实体
public <T> T execute(String serviceId, LoadBalancerRequest<T> request) throws IOException {
    String hint = this.getHint(serviceId);
    LoadBalancerRequestAdapter<T, DefaultRequestContext> lbRequest = new LoadBalancerRequestAdapter(request, new DefaultRequestContext(request, hint));
    Set<LoadBalancerLifecycle> supportedLifecycleProcessors = this.getSupportedLifecycleProcessors(serviceId);
    supportedLifecycleProcessors.forEach((lifecycle) -> {
        lifecycle.onStart(lbRequest);
    });
  	//可以看到在这里会调用choose方法自动获取对应的服务实例信息
    ServiceInstance serviceInstance = this.choose(serviceId, lbRequest);
    if (serviceInstance == null) {
        supportedLifecycleProcessors.forEach((lifecycle) -> {
            lifecycle.onComplete(new CompletionContext(Status.DISCARD, lbRequest, new EmptyResponse()));
        });
      	//没有发现任何此服务的实例就抛异常(之前的测试中可能已经遇到了)
        throw new IllegalStateException("No instances available for " + serviceId);
    } else {
      	//成功获取到对应服务的实例,这时就可以发起HTTP请求获取信息了
        return this.execute(serviceId, serviceInstance, lbRequest);
    }
}

feign用的是ribbon还是loadbal,SpringCloud &amp; Alibaba,负载均衡,java,spring boot 

c)因此,实际上,在进行负载均衡的时候,会向服务的注册中心(Nacos)发起一个请求,选择一个可用的服务(如果有多个),然后返回此服务的主机地址等信息.

二、整合 OpenFeign + LoadBalancer


2.1、所需依赖

在需要进行远程调用的服务中引入openfeign 和 loadbalancer 依赖

        <dependency>
            <groupId>org.springframework.cloud</groupId>
            <artifactId>spring-cloud-starter-openfeign</artifactId>
        </dependency>

        <dependency>
            <groupId>org.springframework.cloud</groupId>
            <artifactId>spring-cloud-starter-loadbalancer</artifactId>
        </dependency>

2.2、具体实现

a)启动类中添加 @EnableFeignClients 注解

@SpringBootApplication
@EnableFeignClients
public class UserApplication {

    public static void main(String[] args) {
        SpringApplication.run(UserApplication.class, args);
    }

}

b)例如,在 user 微服务中调用 article 微服务接口,那么就需要在 user 为服务中创建一个 article 的客户端.

@FeignClient("article")
public interface ArticleClient {

    @GetMapping("/article/start")
    String userStart();

}

服务提供者:

@RestController
@RequestMapping("/article")
public class ArticleController {

    @GetMapping("/start")
    public String userStart() {
        System.out.println("article 被远程调用了!");
        return "article ok ~";
    }

}

服务消费者:

@RestController
@RequestMapping("/user")
public class UserController {

    @Autowired
    private ArticleClient articleClient;

    @GetMapping("/start")
    public String userStart() {
        String result = articleClient.userStart();
        return "user ok ~\n" + result;
    }

}

c)访问 user 服务接口,可以看到成功进行了远程调用

feign用的是ribbon还是loadbal,SpringCloud &amp; Alibaba,负载均衡,java,spring boot

d)连续访问 10 次,可以发现,在 OpenFeign 的声明式客户端中,不用加 @LoadBalancer 注解也会实现默认的 “轮询” 负载均衡策略(RestTemplate 方式必须加).

feign用的是ribbon还是loadbal,SpringCloud &amp; Alibaba,负载均衡,java,spring boot

 feign用的是ribbon还是loadbal,SpringCloud &amp; Alibaba,负载均衡,java,spring boot

在 BlockingLoadBalancerClient 中添加断点,就可以看到我们指定的策略默认是轮询(RoundRobin):

feign用的是ribbon还是loadbal,SpringCloud &amp; Alibaba,负载均衡,java,spring boot

 2.3、自定义负载均衡策略

LoadBalancer默认提供了两种负载均衡策略:

  • RandomLoadBalancer - 随机分配策略
  • (默认) RoundRobinLoadBalancer - 轮询分配策略

现在希望修改默认的负载均衡策略为随机分配策略,就需要创建随机分配策略的配置类(不用加 @Configuration):

//这里不用加 @Configuration 注解
public class LoadBalancerConfig {
    //将官方提供的 RandomLoadBalancer 注册为Bean
    @Bean
    public ReactorLoadBalancer<ServiceInstance> randomLoadBalancer(Environment environment, LoadBalancerClientFactory loadBalancerClientFactory){
        String name = environment.getProperty(LoadBalancerClientFactory.PROPERTY_NAME);
        return new RandomLoadBalancer(loadBalancerClientFactory.getLazyProvider(name, ServiceInstanceListSupplier.class), name);
    }
}

通过 @LoadBalancerClient(value = "服务名", configuration = LoadBalancerConfig.class)  指定负载均衡策略为随机.

@FeignClient("article")
@LoadBalancerClient(value = "article", configuration = LoadBalancerConfig.class) //指定负载均衡策略为随机
public interface ArticleClient {

//    @LoadBalanced(可以写,也可以不用写,默认所有方法都自动加 @LoadBalanced)
    @GetMapping("/article/start")
    String userStart();

}

feign用的是ribbon还是loadbal,SpringCloud &amp; Alibaba,负载均衡,java,spring boot

feign用的是ribbon还是loadbal,SpringCloud &amp; Alibaba,负载均衡,java,spring boot文章来源地址https://www.toymoban.com/news/detail-768745.html

到了这里,关于SpringCloud - 新版淘汰 Ribbon,在 OpenFeign 中整合 LoadBalancer 负载均衡的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处: 如若内容造成侵权/违法违规/事实不符,请点击违法举报进行投诉反馈,一经查实,立即删除!

领支付宝红包 赞助服务器费用

相关文章

  • Java之SpringCloud Alibaba【五】【微服务 Sentinel整合openfeign进行降级】

    Java之SpringCloud Alibaba【一】【Nacos一篇文章精通系列】 跳转 Java之SpringCloud Alibaba【二】【微服务调用组件Feign】 跳转 Java之SpringCloud Alibaba【三】【微服务Nacos-config配置中心】 跳转 Java之SpringCloud Alibaba【四】【微服务 Sentinel服务熔断】 跳转 Java之SpringCloud Alibaba【五】【微服务

    2024年02月11日
    浏览(32)
  • springcloud 中RestTemplate 是怎么和 ribbon整合,实现负载均衡的?源码分析

    RestTemplate 内置了一个 ClientHttpRequestInterceptor ,这个是一个拦截器操作,我们可以在请求的前后做一些事情。然后我们看一下这个类,这个类里面 有一个 intercept 方法。我们看下这个实现类,里面有一个 LoadBalancerInterceptor 实现类。 我们来看 LoadBalancerInterceptor 实现类。 然后我

    2024年02月09日
    浏览(29)
  • 微服务 springcloud 08.zuul框架,API网关,整合ribbon和hystrix框架

    01.zuul是作为springcloud中的一个网关框架来使用的。 zuul API 网关,为微服务应用提供统一的对外访问接口。 zuul 还提供过滤器,对所有微服务提供统一的请求校验。 在项目中的位置: 02.新建 sp11-zuul 项目 03.pom.xml 需要添加 sp01-commons 依赖 04.application.yml zuul 路由配置可以省略,

    2024年02月09日
    浏览(28)
  • LoadBalancer 替换 Ribbon

    POM 移除 Ribbon 相关依赖 配置文件中禁用 Ribbon

    2024年01月16日
    浏览(27)
  • 客户端负载均衡策略:loadBalancer,ribbon

    客户端负载均衡是指在分布式系统中,客户端通过某种策略将请求分发到多个服务提供者实例上,以达到负载均衡和提高系统的可用性和性能。 在 Java 生态系统中,Ribbon 是一个常用的客户端负载均衡框架,它是 Netflix 开源的一部分,被广泛应用于 Spring Cloud 中。Ribbon 提供了

    2024年02月08日
    浏览(37)
  • 《Spring Cloud学习笔记:Nacos配置管理 & OpenFeign & LoadBalancer & Getway》

    基于Feign的声明式远程调用(代码更优雅),用它来去代替我们之前的RestTemplate方式的远程调用 首先我们来看一下,微服务架构下关于配置文件的一些问题: 配置文件相对分散。在一个微服务架构下,配置文件会随着微服务的增多变的越来越多,而且分散在各个微服务中,不

    2024年02月04日
    浏览(37)
  • Spring Cloud Alibaba全家桶(三)——微服务负载均衡器Ribbon与LoadBalancer

    本文为 微服务负载均衡器Ribbon与LoadBalancer 相关知识,下边将对 什么是Ribbon (包括: 客户端的负载均衡 、 服务端的负载均衡 、 常见负载均衡算法 ), Nacos使用Ribbon , Ribbon内核原理 (包括: Ribbon原理 , Ribbon负载均衡策略 , 饥饿加载 ), Spring Cloud LoadBalancer (包括:

    2024年02月02日
    浏览(32)
  • 最新版 !快速掌握 JDK17 + springboot3 + springcloud Alibaba : 10、Seata 整合实现分布式事务

    上一节成功启动了seata,传送门: https://blog.csdn.net/qq_16089135/article/details/133989446 1.1 官方文档 中文文档 Seata 是什么 1.2 模式分类 AT :基于支持本地 ACID 事务的关系型数据库。 Java 应用,通过 JDBC 访问数据库。 整体机制:二阶段提交。 一阶段:业务数据和回滚日志记录在同一

    2024年02月06日
    浏览(42)
  • springCloud-LoadBalancer负载均衡微服务负载均衡器LoadBalancer

    2020年前SpringCloud是采用Ribbon作为负载均衡实现,但是在2020后采用了LoadBalancer替代 1.RandomLoadBalancer-随机分配策略 2.RoundRobinLoadBalancer-轮询分配策略(默认)

    2024年04月15日
    浏览(41)
  • springCloud-LoadBalancer负载均衡

    Eureka主要是如何通过eureka服务器进行服务注册与发现,也有简单的负载均衡,实际上它其中的负载均衡就是靠LoadBalancer实现的。 2020年前SpringCloud是采用Ribbon作为负载均衡实现,但是在2020后采用了LoadBalancer替代。 LoadBalancer默认提供了两种负载均衡策略。 1.RandomLoadBalancer-随机分

    2024年02月09日
    浏览(26)

觉得文章有用就打赏一下文章作者

支付宝扫一扫打赏

博客赞助

微信扫一扫打赏

请作者喝杯咖啡吧~博客赞助

支付宝扫一扫领取红包,优惠每天领

二维码1

领取红包

二维码2

领红包