Ribbon负责均衡原理图
源码详解:
@LoadBalanced
标记RestTemplate发起的请求,会被loadBalanced拦截和处理
/**
* 创建RestTemplate并注入Spring容器
*/
@Bean
@LoadBalanced
public RestTemplate restTemplate() {
return new RestTemplate();
}
拦截的动作是由 LoadBalancerInterceptor执行的,
LoadBalancerInterceptor实现了一个接口ClientHttpRequestInterceptor
ClientHttpRequestInterceptor 是一个客户端http请求的拦截器
回去拦截有客户端发起的http请求
final URl originalUri = request.getURI(); 这里获取的时初始url,配置里挖法访问的一个服务地址
originalUri.getHost 来获取对应的服务名serviceName
然后通过 this.loadBalancer.execute() 来处理,
loadBalancer时一个名为RibbonLoadBalancerClient的对象。这里Ribbon开始介入
如上图: getServer() 来获取服务列表
下一步选择服务,如何选择服务呢,这时候 调用chooseServer()方法
这里调用super.chooseServer(),继续往下走
这里走到练了rule.choose(); rule这里代表了选择规则,指向了IRule
IRule 的实现类有很多规则,默认使用 ZoneAvoidanceRule,如下:
RoundRobinRule
RandomRule
RetryRule
ClientCOnfigEnabledRoundRobinRule
过则说明:
如何修改规则的实现呢:
实现方法一:
在application中,定义一个规则,使用哪个规则根据自己的实际情况选择,这种方法时全局的
@Bean
public IRule randomRule() {
return new RoundRobinRule();
}
@Bean
public IRule randomRule() {
return new RandomRule();
}
实现方法二:
在相对应的服务下的 application.yml中配置,这种方法是针对某个具体服务的
userservice:
ribbon:
NFLoadBalancerRuleClassName: com.netflix.loadbalancer.RandomRule # 负载均衡规则