Ribbon 负载均衡实现

矫情吗;* 2023-10-04 22:49 119阅读 0赞

1. 依赖

  1. <dependency>
  2. <groupId>org.springframework.cloud</groupId>
  3. <artifactId>spring-cloud-starter-netflix-ribbon</artifactId>
  4. </dependency>

2. 配置

  1. my-service:
  2. ribbon:
  3. listOfServers: example.com:8080, example.net:8080

常用配置项:
ribbon.eureka.enabled:指定是否启用Ribbon与Eureka服务器集成。默认为true。

ribbon.client.name:指定Ribbon客户端的名称。当使用Spring Cloud Netflix时,该值通常是服务名。

ribbon.NFLoadBalancerRuleClassName:指定负载均衡算法的类名。如果未指定,则使用默认的RoundRobinRule算法。

ribbon.ReadTimeout:指定读取超时时间,以毫秒为单位。如果在此时间内没有收到响应,则请求将被中断。

ribbon.ConnectTimeout:指定连接超时时间,以毫秒为单位。如果在此时间内无法建立连接,则请求将被中断。

ribbon.OkToRetryOnAllOperations:指定在发生故障时是否应重试所有操作。默认为false。

ribbon.MaxAutoRetries:指定自动重试操作的最大次数。默认为0,表示不进行自动重试。

ribbon.MaxAutoRetriesNextServer:指定在下一个服务器上进行自动重试的最大次数。默认为1。

ribbon.ServerListRefreshInterval:指定更新服务器列表的间隔时间,以毫秒为单位。

ribbon.ServerListRefreshInitialDelay:指定在第一次更新服务器列表之前的延迟时间,以毫秒为单位。

ribbon.ServerListClassName:指定服务器列表的实现类。如果未指定,则使用默认的ConfigurationBasedServerList实现。

ribbon.ServerListFilterClassName:指定用于筛选服务器列表的类的名称。如果未指定,则不应用任何过滤器。

ribbon.EnablePrimeConnections:指定是否启用Prime Connections。默认为false。

3. 实现

  1. @Configuration
  2. public class MyLoadBalancerConfiguration {
  3. @Bean
  4. public IRule myLoadBalancingRule() {
  5. return new MyLoadBalancingRule();
  6. }
  7. private static class MyLoadBalancingRule extends AbstractLoadBalancerRule {
  8. private AtomicInteger nextServerCyclicCounter;
  9. public MyLoadBalancingRule() {
  10. nextServerCyclicCounter = new AtomicInteger(0);
  11. }
  12. @Override
  13. public Server choose(Object key) {
  14. List<Server> allServers = getLoadBalancer().getAllServers();
  15. if (allServers.isEmpty()) {
  16. return null;
  17. }
  18. int nextServerIndex = incrementAndGetModulo(allServers.size());
  19. return allServers.get(nextServerIndex);
  20. }
  21. private int incrementAndGetModulo(int modulo) {
  22. int current;
  23. int next;
  24. do {
  25. current = nextServerCyclicCounter.get();
  26. next = (current + 1) % modulo;
  27. } while (!nextServerCyclicCounter.compareAndSet(current, next));
  28. return next;
  29. }
  30. }
  31. }

4. 发送请求

  1. @Service
  2. public class MyService {
  3. @Autowired
  4. private RestTemplate restTemplate;
  5. public String callMyService() {
  6. String response = restTemplate.getForObject("http://my-service/path/to/resource", String.class);
  7. return response;
  8. }
  9. }

Ps

其中的循环遍历可用代码的服务器列表的代码是

  1. List<Server> allServers = getLoadBalancer().getAllServers();
  2. if (allServers.isEmpty()) {
  3. return null;
  4. }
  5. int nextServerIndex = incrementAndGetModulo(allServers.size());
  6. return allServers.get(nextServerIndex);

or

  1. private AtomicInteger nextServerCyclicCounter;
  2. public MyLoadBalancingRule() {
  3. nextServerCyclicCounter = new AtomicInteger(0);
  4. }
  5. private int incrementAndGetModulo(int modulo) {
  6. int current;
  7. int next;
  8. do {
  9. current = nextServerCyclicCounter.get();
  10. next = (current + 1) % modulo;
  11. } while (!nextServerCyclicCounter.compareAndSet(current, next));
  12. return next;
  13. }

发表评论

表情:
评论列表 (有 0 条评论,119人围观)

还没有评论,来说两句吧...

相关阅读

    相关 负载均衡Ribbon

    1. Feign 默认集成了 Ribbon Feign 是一个声明式的伪 Http 客户端,它使得写 Http 客户端变得更简单。使用 Feign,只需要创建一个接口并注

    相关 负载均衡---ribbon

    Ribbon:提供云端负载均衡,有多种负载均衡策略可供选择,可配合服务发现和断路器使用。 上一篇简单讲解了eureka的使用,这一篇文章基于上一篇的基础上,讲一下spring

    相关 Ribbon负载均衡

    1. 集中式负载均衡 > 在客户端和服务端之间使用独立的负载均衡设施(可以是硬件,如F5, 也可以是软件,如nginx、LVS等), 由该设施负责把访问请求通过某种策略转发