SpringCloud实战4 - Ribbon实现客户端侧负载均衡

Ribbon简介

   Ribbon有助于控制HTTP和tcp客户端的行为,为ribbon配置服务提供者地址列表后,Ribbon就可以基于某种负载均衡算法吗,自动的帮助服务消费者去请求。Ribbon默认为我们提供很多负载均衡算法,例如轮询,随机等,

  SpringCloud在,当Ribbon和Eureka配合使用时,Ribbon可以自动 从Eureka Server获取服务提供者地址,并基于负载均衡算法,请求其中一个服务提供者实例。

为服务消费者整合Ribbon

   创建一个子模块 在子模块的pom.xml中添加

   

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

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

在启动类添加如下代码

@SpringBootApplication
@EnableDiscoveryClient
public class YmkRibbonConsumerApplication {

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

    //	开启客户端负载均衡
    @LoadBalanced
    @Bean
    RestTemplate restTemplate() {
        return new RestTemplate();
    }
}

   在入口类上添加@EnableDiscoveryClient注解,表示该应用是一个Eureka客户端应用,这样该应用就自动具备了发现服务的能力。 

   RestTemplate可以帮助我们发起一个GET或者POST请求,这个我们在后文会详细解释,这里我们只需要提供一个RestTemplate  Bean就可以了,在提供Bean的同时,添加@LoadBalanced注解,表示开启客户端负载均衡

  添加一个控制器

  

@RestController
public class HelloController {

    @Autowired
    RestTemplate restTemplate;

    @RequestMapping(value = "/hello", method = RequestMethod.GET)
    public String hello(@RequestParam String name) {
        ResponseEntity<String> responseEntity = restTemplate.getForEntity("http://provider/hello?name={1}", String.class,name);
        return responseEntity.getBody();
    }


}

   添加application.yml 配置

   

server:
  port: 8010
spring:
  application:
    name: ribbon-consumer
eureka:
  client:
    serviceUrl:
      defaultZone: http://peer1:8761/eureka/,http://peer2:8762/eureka/
  instance:
    prefer-ip-address: true

      回到服务提供者项目,添加一行打印,用来测试是否有负载均衡的效果   

@RestController
public class TestController implements TestService{

    @RequestMapping(value = "/hello", method = RequestMethod.GET)
    public String hello(String name) {
        System.out.println("Hello "+name);
        return "Hello "+name;
    }
}

  现在启动所有的项目,并开始测试。以此启动服务注册中心项目,服务提供者项目,服务消费者项目

  可以看到

  

  现在访问 http://localhost:8010/hello?name=ribbon

  

多次访问地址,然后看下控制台的打印

 

   两个提供者项目都打印了,说明我们这里的负载均衡已经起作用了。

Ribbon配置自定义

   很多场景下,可能需要自定义的Ribbon配置,例如修改Ribbon的负载均衡规则等。允许使用java代码或属性自定义Ribbon的配置。两种方式等价的。

使用java代码自定义Ribbon配置

   在Springcloud中Ribbon默认的配置类是RibbonClientConfiguration。也可使用一个POJO自定义的Ribbon的配置。(自定义的配置会覆盖掉默认配置)。这种配置是细粒度的,不同名称的Ribbon客户端可以使用不同的配置。

   创建一个Ribbon的配置类,新建一个包,然后新建类RibbonConfiguration,该类不应该在主应用程序上下文的@ComponentScan 中。

/**
 * 该类为Ribbon的配置类
 * 注意:该类不应该在主应用程序上下文的@ComponentScan 中。
 */
@Configuration
public class RibbonConfiguration {
  @Bean
  public IRule ribbonRule() {
    // 负载均衡规则,改为随机
    return new RandomRule();
  }
}

   创建一个空类,并在其上添加@Configuration注解和@RibbonClient注解。   

@Configuration
@RibbonClient(name = "provider", configuration = RibbonConfiguration.class)
public class TestConfiguration {
}

   由上代码可知,使用@RibbonClient注解的configuration属性,可以自定义指定名称的Ribbon客户端。

   在消费者项目添加如下代码,用来测试

   

 @GetMapping("/log-user-instance")
    public void logUserInstance() {
        ServiceInstance serviceInstance = this.loadBalancerClient.choose("provider");
        // 打印当前选择的是哪个节点
        System.out.println("{}:{}:{}," + serviceInstance.getServiceId()+","+ serviceInstance.getHost()+","+ serviceInstance.getPort());
    }

   多次调用 http://localhost:8010/log-user-instance ,观查控制台打印结果。如下 负载均衡规则,已经由原来的轮询改为随机了。 

    

   全部配置 

  可以使用@RibbonClients 为所有的Ribbon 提供默认配置,如下

@RibbonClients(defaultConfiguration = RibbonConfiguration.class)
public class TestConfiguration {
}

   多次调用 http://localhost:8010/log-user-instance ,观查控制台打印结果

    

   效果一样的。

   使用属性自定义Ribbon配置

      相对于java代码配置,简单不小,只需要在application.yml 中添加如下配置即可

      

provider:
  ribbon:
    NFLoadBalancerRuleClassName: com.netflix.loadbalancer.RandomRule

   这样就可以将名为 provider 的负载均衡设置为随机。

   多次调用 http://localhost:8010/log-user-instance ,观查控制台打印结果      

   全局配置

   由于spring-cloud的Ribbon并没有实现netflix Ribbon的所有配置项。netflix配置全局rule方式为:ribbon.NFLoadBalancerRuleClassName=com.netflix.loadbalancer.RandomRule,但是 spring-cloud并不支持,spring-cloud直接到服务粒度,只支持SERVICE_ID.ribbon.NFLoadBalancerRuleClassName=com.netflix.loadbalancer.RandomRule

 脱离Eureka 使用Ribbon 

   因为往往Ribbon配合Eureka使用的,往往也有第三方服务没有注册到Eureka Server,甚至不是spring cloud开发的,也需要进行负载均衡,这时可以在服务消费者的配置文件中进行如下方式配置,实现负载均衡

serverId:
   ribbon:
      listOfServers:localhost:8010,localhost:8011

   listOfServers属性用于为名为serverId的ribbon客户端设置的请求的地址列表。

 

属性配置的方式比java代码配置的方式具有更高的优先级。

更多关于RestTemplate的请求方式,以及参数的传递,参考此链接 : https://blog.csdn.net/keehom/article/details/80721599

 

源码下载: https://download.csdn.net/download/u013083284/10749566

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值