SpringCloud-16-切换及自定义负载均衡策略

在人生的道路上,不管是潇洒走一回,或者是千山独行,皆须是自己想走的路,虽然,有的人并不是很快就能找到自己的方向和道路,不过,只要坚持到底,我相信,就一定可以找到自己的路,只要找到路,就不必怕路途遥远了。

导读:本篇文章讲解 SpringCloud-16-切换及自定义负载均衡策略,希望对大家有帮助,欢迎收藏,转发!站点地址:www.bmabk.com,来源:原文

6.5 切换负载均衡策略

  • Spring Cloud Ribbon 默认使用轮询策略选取服务实例,我们也可以根据自身的需求切换负载均衡策略。
  • 对于切换负载均衡策略,只需要在服务消费者(客户端)的配置类中,将 IRule 的其他实现类注入到容器中即可。
6.5.1 第一种方式 使用配置类
  • 例如:在 microservice-cloud-consumer-dept-80 的配置类 ConfigBean 中添加以下代码,将负载均衡策略切换为 RandomRule(随机)。
@Bean
public IRule myIRule(){
    // RandomRule 为随机策略
    return new RandomRule();
}

切换负载均衡策略和自定义负载均衡策略需要导入低版本的spring-cloud-starter-netflix-eureka-client。由于使用的spring-cloud-starter-netflix-eureka-client版本太高,并且没有实现@LoadBalanced接口,就会报错需要实现 LoadBalanceClient 接口。而Ribbon需要结合具体的客户端去实现。同时如果不在项目中实现该接口,必须使用带有与ribbon结合的工具库的包如图所示(新版本已将其丢弃)

<dependency>
            <groupId>org.springframework.cloud</groupId>
            <artifactId>spring-cloud-starter-netflix-eureka-client</artifactId>
            <version>2.2.10.RELEASE</version>
        </dependency>
  • 3.0.4版本
    在这里插入图片描述
  • 2.2.9.RELEASE版本
    在这里插入图片描述

在导入依赖时,尽可能让前缀相同的依赖使用相同的版本!

  • 在 microservice-cloud-consumer-dept-80 的主启动类上,使用 @RibbonClients 注解来让我们切换的的负载均衡策略生效,代码如下。
package com.example;

import com.example.config.FeignConfiguration;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.cloud.netflix.eureka.EnableEurekaClient;
import org.springframework.cloud.netflix.ribbon.RibbonClient;
import org.springframework.cloud.netflix.ribbon.RibbonClients;
import org.springframework.cloud.openfeign.EnableFeignClients;

//OpenFeign和Eureka整合以后,容户端可以直接调用用,不用关心服务的IP地址和端口号
@SpringBootApplication
@EnableEurekaClient
// 如果只有一个服务就可以直接使用@RibbonClient注解,而不需要@RibbonClients。
// name是写服务提供方的服务名     configuration是指定我们上面创建的配置类
@RibbonClients(value = {
        @RibbonClient(name = "MICROSERVICECLOUDPROVIDERDEPT",configuration = FeignConfiguration.class)
})
//@RibbonClient(name = "MICROSERVICECLOUDPROVIDERDEPT",configuration = FeignConfiguration.class)
public class MicroserviceCloudConsumerDeptOpenFeignApplication {

    public static void main(String[] args) {
        SpringApplication.run(MicroserviceCloudConsumerDeptOpenFeignApplication.class, args);
    }
}
  • 重启 microservice-cloud-consumer-dept-80,使用浏览器访问“http://eurekaserver7001.com/app/consumer/dept/list”或http://localhost/app/consumer/dept/list,结果如下图。负载均衡策略切换为 RandomRule(随机)。不断刷新链接,发现数据来源集中于springcloud_db3和springcloud_db_core
    在这里插入图片描述
    在这里插入图片描述
6.2.2 第二种方式 使用yaml配置
  • 在 micro-service-cloud-provider-dept-8003 中 application.yml 中,修改的这种负载均衡算法
#设置负载均衡策略 eureka-provider 为调用的服务的名称  value为策略全限定名
eureka-provider:
  ribbon:
    NFLoadBalancerRuleClassName: com.netflix.loadbalancer.RandomRule

6.6 自定义负载均衡策略

  • 通常情况下,Ribbon 提供的这些默认负载均衡策略是可以满足我们的需求的,如果有特殊的要求,我们还可以根据自身需求定制负载均衡策略。
  • 测试下自定义负载均衡策略,在 microservice-cloud-consumer-dept-80 中新建一个 com.myrule 包,并在该包下创建一个名为 MyRibbonRule的类(里面具体的实现可以仿照Ribbon下loadbalancer的接口IRule的实现类RandomRule),代码如下。
package com.myrule;

import com.netflix.loadbalancer.AbstractLoadBalancerRule;
import com.netflix.loadbalancer.ILoadBalancer;
import com.netflix.loadbalancer.Server;

import java.util.List;

/**
 * 定制 Ribbon 负载均衡策略
 */

public class MyRibbonRule extends AbstractLoadBalancerRule{

    private int index = 0;    // 当前提供服务的机器号
    private int total = 0; //总共被调用的次数,目前要求每台被调用3次

    public MyRibbonRule() {
        super();
    }

    @Override
    public void setLoadBalancer(ILoadBalancer lb) {
        setLoadBalancer(lb);
    }

    @Override
    public ILoadBalancer getLoadBalancer() {
        return getLoadBalancer();
    }

    @Override
    public Server choose(Object key) {
        return null;
    }
    public Server choose(ILoadBalancer lb, Object key) {
        if (lb == null) {
            return null;
        }
        Server server = null;
        while (server == null) {
            if (Thread.interrupted()) {
                return null;
            }
            //获取所有有效的服务实例列表
            List<Server> upList = lb.getReachableServers();
            //获取所有的服务实例的列表
            List<Server> allList = lb.getAllServers();
            //如果没有任何的服务实例则返回 null
            int serverCount = allList.size();
            if (serverCount == 0) {
                return null;
            }
            if(total < 3){
            	//从有效的服务选择   index = (total++)/ 3 % 3  0开始
                server = upList.get(index);      
                total++;
            }else {
                total = 0;
                index++;
                if (index >= upList.size()){
                    index = 0;
                }
            }
            if (server == null) {
                Thread.yield();
                continue;
            }
            if (server.isAlive()) {
                return (server);
            }
            server = null;
            Thread.yield();
        }
        return server;
    }
}
  • 在 com.myrule 包下创建一个名为 MyRibbonRuleConfig 的配置类,将我们定制的负载均衡策略实现类注入到容器中,代码如下。

该自定义 Ribbon 负载均衡策略配置类不能在 com.example 包及其子包下也就是不能和启动类同级,否则将会被启动类扫描到@ComponentScan导致所有的 Ribbon客户端都会采用该策略,无法达到特殊化定制的目的

package com.myrule;

import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
//定制 Ribbon 负载均衡策略的配置类
@Configuration
public class MyRibbonRuleConfig {
    @Bean
    public MyRibbonRule myRibbonRule(){
        return new MyRibbonRule();
    }
}
  • 修改位于 com.example包下的主启动类,在该类上使用 @RibbonClient 注解让我们定制的负载均衡策略生效。
  • 自定义 Ribbon 负载均衡策略在主启动类上使用 RibbonClient 注解,在该微服务启动时,就能自动去加载我们自定义的 Ribbon 配置类,从而使默认配置生效
  • name 为需要定制负载均衡策略的微服务名称(application name)
  • configuration 为定制的负载均衡策略的配置类
  • 官方文档中明确提出,该配置类不能在 ComponentScan 注解(SpringBootApplication 注解中包含了该注解)下的包或其子包中,即自定义负载均衡配置类不能在 com.example 包及其子包下
//Ribbon和Eureka整合以后,容户端可以直接调用用,不用关心服务的IP地址和端口号
@SpringBootApplication
@EnableEurekaClient
//在微服务启动的时就能去加载我们自定义Ribbon类
@RibbonClient(name = "MICROSERVICECLOUDPROVIDERDEPT",configuration = MyRibbonRuleConfig.class)
public class MicroserviceCloudConsumerDept80Application {

    public static void main(String[] args) {
        SpringApplication.run(MicroserviceCloudConsumerDept80Application.class, args);
    }
}
  • 重启 microservice-cloud-consumer-dept-80,使用浏览器访问“http://localhost/app/consumer/dept/list”,结果如下图。同一个服务的数据刷新5次后,改变为另一个服务的数据
    在这里插入图片描述
    在这里插入图片描述

  • 从上图中的dbSource 字段取值的变化可以看出,我们定制的负载均衡策略已经生效。

下一篇:SpringCloud-17-OpenFeign:Feign 介绍

版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 举报,一经查实,本站将立刻删除。

文章由极客之音整理,本文链接:https://www.bmabk.com/index.php/post/123812.html

(0)
飞熊的头像飞熊bm

相关推荐

发表回复

登录后才能评论
极客之音——专业性很强的中文编程技术网站,欢迎收藏到浏览器,订阅我们!