SpringCloud学习笔记(三):Ribbon和Feign负载均衡

SpringCloud Ribbon是基于Netflix Ribbon实现的一套客户端负载均衡的工具。

简单的说,Ribbon是Netflix发布的开源项目,主要功能是提供客户端的软件负载均衡算方法,将Netflix的中间服务连接在一起。Ribbon客户端主键提供一系列完善的配置项如何连接超时,重试等,就是在配置文件中列出Load Balancer(简称LB)后面所有的机器,Ribbon会自动的帮助你基于某种规则(如简单轮询,随机连接等)去连接这些机器。我们也很容易使用Ribbon实现自定义的负载均衡算法。

一、Ribbon的配置

1.修改pom文件

<dependency>
    <groupId>org.springframeword.cloud </groupId>
    <artifactId>spring-cloud-starter-eureka</artifactId>
</dependency>

<dependency>
    <groupId>org.springframeword.cloud</groupId>
    <artifactId>spring-cloud-starter-ribbon</artifactId>
</dependency>

<dependency>
    <groupId>org.springframeword.cloud</groupId>
    <artifactId>spring-cloud-starter-config</artifactId>
</dependency>

2.修改配置文件

eureka:
    client: #客户端注册Eureka服务列表内
        register-with-eureka:false
        service-url:
            defaultZone:http://eureka7001.com:7001/eureka/,http://eureka7002.com:7002/eureka/,http://eureka7003.com:7003/eureka/

3.修改bean的注入配置

@Bean
@LoadBalanced   //负载均衡
public RestTemplate getRestTemplate(){
    return new RestTemplate;
}

4.修改主启动类

@SpringBootApplication
@EnableEurekaClient  //本服务启动后悔自动注册进Eureka服务中
public class DeptConsumer80_App{
    SpringApplication.run(DeptConsumer80_App.class,args);
}

5.修改微服务端口

//private static final String REST_URL_PREFIX="http://localhost:8001"  
//修改成
private static final String REST_URL_PREFIX="http://MICROSERCICECLOUD-DEPT"

Ribbon和Eureka整合后Consumer可以直接调用服务而不再关心地址和端口号

二、Ribbon实现负载均衡

Ribbon在工作时分成两步

第一步先选择EurekaService它优先选择在同一个区域内负载较少的server

第二步根据用户指定的策略,在从Server取到服务器注册列表中选择一个地址

同一个服务在多实例的时候对外暴露的服务名称要相同

Ribbon其实就是一个软负载均衡的客户端组件,他可以和其他的所需请求的客户端结合使用,和eureka结合只是其中一个实例。

三、Ribbon核心组件IRule

  1. RoundRobinRule:轮询

  2. RandomRule:随机

  3. AvailabilityFilteringRule:会先过滤掉由于多次访问故障而处于断路器跳闸状态的服务器,还有并发的连接数超过阈值的服务,然后对剩余的服务器列表按照轮询策略进行访问

  4. WeightedResponseTimeRule:根据平均响应时间计算所有服务器的权重,响应时间越快服务权重越大被选中的概率越高。刚启动时如果统计信息不足,则使用RoundRobinRule策略,等统计信息足够,会切换回来

  5. RetryRule:先按照RoundRobinRule的策略获取服务,如果获取服务失败则在指定时间内会进行重试,获取可用的服务

  6. BestAvailableRule:会先过滤掉由于多次访问故障而处于断路器跳闸状态的服务器,然后选择一个并发量最小的服务器

  7. ZoneAvoidanceRule:默认规则,复合判断Server所在区域的性能和server的可用性选择服务器

使用IRule切换负载均衡策略

添加Bean

@Bean
public IRule myRule(){
    return new RoundRobinRule(); //new 的对象就是选择的负载均衡策略
}

四、Ribbon自定义策略

1.修改主启动类,添加注解

@SpringBootApplication
@EnableEurekaClient  //本服务启动后悔自动注册进Eureka服务中
//在启动该微服务的时候就能去加载我们自定义的Ribbon配置类,从而使配置生效
//解释:针对MICROSERVICECLOUD-DEPT这个服务,使用configuration=MySelfRule.class的负载均衡策略
@RibbonClient(name="MICROSERVICECLOUD-DEPT",configuration=MySelfRule.class)
public class DeptConsumer80_App{
    SpringApplication.run(DeptConsumer80_App.class,args);
}

2.编写自定义负载均衡策略

注:这个自定义配置类不能放在@ComponentScan所扫描的当前包以及子包下,否则我们自定义的这个配置类就会被所有的Ribbon客户端所共享,也就是说我们达不到特殊定制化的目的了

2.1新建一个包com.xxxx.myrule,创建类MySelfRule

@Configuration
public class MyselfRule(){
    @Bean
    public IRule myRule(){
        return new RandomRule_ZY();
    }
}

RandomRule_ZY

public class RandomRule_ZY extends AbstractLoadBalancerRule(){
    Random rand;

    public RandomRule_ZY(){
        rand = new Random();
    }

    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();
            int serverCount = allList.size();
            if(serverCount == 0){
                return null;
            }

            int index = rand.nextInt(serverCount);
            server = upList.get(index);
            if(server == null){
                Thread.yield();
                continue;
            }

            if(server.isAlive()){
                return (server);
            }
            server = null;
            Thread.yield();
        }
        return server;
    }

    @Override
    public Server Choose(Object key){
        return choose(getLoadBalancer(),key);
    }

    @Override
    public void initWithNiwsConfig(IClientConfig clientConfig){
    }
}

五、Feign

        Feign是一个声明式WebServer客户端。使用Feign能让编写WebService客户端更加简单,他的使用方法是定义一个接口,然后在上面加上注解,同时也支持JAX-RS标准的注解。Feign也支持可拔插式的编码器和解码器。SpringCloud对Feign进行了封装,使其支持了SpringMVC标准注解,和HttpMessageConverters。Feign可以与Eureka和Ribbon组合使用以支持负载均衡。

        Feign可以实现通过接口+注解,获得调用服务,可以依旧使用面向接口的编程方式

1.建立新的工程,修改pom文件

<dependency>
    <groupId>org.springframeword.cloud</groupId>
    <artifactId>spring-cloud-starter-feign</artifactId>
</dependency>

2.创建接口

@FeignClient(value = "MICROSERVICECLOUD-DEPT")
public interface DeptClientService{
    @RequestMapping(value = "/dept/get/{id}",method = RequsetMethod.GET)
    public Dept get(@PathVariable("id")long id);

    @RequestMapping(value = "/dept/list",method = RequsetMethod.GET)
    public List<Dept> list();

    @RequestMapping(value = "/dept/add",method = RequsetMethod.POST)
    public boolean add(Dept dept);
}

3.创建Controller

@RestController
public interface DeptController_Consumer{
    @Autowired
    private DeptClientService service;

    @RequestMapping(value = "/dept/get/{id}")
    public Dept get(@PathVariable("id")long id){
        return service.get(id);
    }

    @RequestMapping(value = "/dept/list")
    public List<Dept> list(){
        return service.list();
    }

    @RequestMapping(value = "/dept/add")
    public boolean add(Dept dept){
        return service.add(dept);
    }
}

4.修改主启动类

@SpringBootApplication
@EnableEurekaClient
//注明扫描范围
@EnableFeignClients(basePackages = {com.xxx.springcloud})
@ComponentScan("com.xxx.springcloud")
public class DeptConsumer80_App{
    SpringApplication.run(DeptConsumer80_App.class,args);
}

Feign集成了Ribbon

利用Ribbon维护了MicroServiceCloud-Dept的服务列表信息,并通过轮询实现了客户端的负载均衡。而与Ribbon不同的是,通过feign只需要定义服务绑定接口且以声明式的方法,优雅而简单的实现了服务调用

猜你喜欢

转载自blog.csdn.net/qq_34886352/article/details/81456748