springcloud-负载均衡


一、负载均衡的基本概念

1.1 什么是负载均衡

负载均衡是指将流量分发到多个服务器以均衡负载,提升系统的可用性和性能。它可以在多个层级实现:

  • 客户端负载均衡:请求由客户端直接分发给不同的服务实例。
  • 服务端负载均衡:请求由负载均衡器(如 Nginx)转发到服务实例。
1.2 Spring Cloud 的负载均衡

Spring Cloud 提供了两种负载均衡机制:

  1. Ribbon:Spring Cloud Netflix 提供的客户端负载均衡器,已在新版 Spring Cloud 中被弃用。
  2. Spring Cloud LoadBalancer:Spring Cloud 提供的官方负载均衡实现,从 Spring Cloud 2020 开始推荐使用。

二、负载均衡的策略

Spring Cloud 支持多种负载均衡策略,常见的有:

  1. 轮询(RoundRobin)
    • 按照顺序依次将请求分发到各服务实例。
  2. 随机(Random)
    • 随机选择一个服务实例处理请求。
  3. 权重(Weighted)
    • 根据服务实例的权重分发请求。
  4. 基于响应时间(Best Available)
    • 优先将请求分发到响应时间最短的实例。

开发者可以选择默认策略,也可以通过自定义策略满足业务需求。


三、Spring Cloud LoadBalancer 配置与使用

3.1 添加依赖

在 Maven 项目中添加 spring-cloud-starter-loadbalancer 依赖。

<dependencies>
    <dependency>
        <groupId>org.springframework.cloud</groupId>
        <artifactId>spring-cloud-starter-loadbalancer</artifactId>
    </dependency>
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-web</artifactId>
    </dependency>
    <dependency>
        <groupId>org.springframework.cloud</groupId>
        <artifactId>spring-cloud-starter-netflix-eureka-client</artifactId>
    </dependency>
</dependencies>
3.2 配置 Eureka 注册中心

application.yml 示例:

spring:
  application:
    name: client-service
  cloud:
    loadbalancer:
      retry: true # 启用重试机制
  eureka:
    client:
      service-url:
        defaultZone: http://localhost:8761/eureka/
3.3 配置服务提供者

注册多个实例到 Eureka,模拟负载均衡。假设有两个服务实例:

  1. provider-service1:运行在 http://localhost:8081
  2. provider-service2:运行在 http://localhost:8082

四、Spring Cloud LoadBalancer 的实现

以下示例通过 RestTemplateWebClient 演示负载均衡的使用。

4.1 RestTemplate 方式
创建配置类
import org.springframework.cloud.client.loadbalancer.LoadBalanced;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.web.client.RestTemplate;

@Configuration
public class RestTemplateConfig {

    @Bean
    @LoadBalanced // 开启负载均衡
    public RestTemplate restTemplate() {
        return new RestTemplate();
    }
}
使用 RestTemplate 调用服务
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RestController;
import org.springframework.web.client.RestTemplate;

@RestController
public class LoadBalancerController {

    @Autowired
    private RestTemplate restTemplate;

    @GetMapping("/invoke")
    public String invokeProvider() {
        // 通过服务名调用服务
        String url = "http://provider-service/hello";
        return restTemplate.getForObject(url, String.class);
    }
}

4.2 WebClient 方式
创建配置类
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.web.reactive.function.client.WebClient;

@Configuration
public class WebClientConfig {

    @Bean
    public WebClient.Builder webClientBuilder() {
        return WebClient.builder();
    }
}
使用 WebClient 调用服务
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RestController;
import org.springframework.web.reactive.function.client.WebClient;

@RestController
public class LoadBalancerController {

    @Autowired
    private WebClient.Builder webClientBuilder;

    @GetMapping("/invokeWebClient")
    public String invokeProviderWithWebClient() {
        return webClientBuilder.build()
                .get()
                .uri("http://provider-service/hello")
                .retrieve()
                .bodyToMono(String.class)
                .block();
    }
}

五、自定义负载均衡策略

5.1 自定义配置类

通过实现 ReactorServiceInstanceLoadBalancer 接口来自定义负载均衡策略。

import org.springframework.cloud.client.ServiceInstance;
import org.springframework.cloud.client.loadbalancer.ReactorServiceInstanceLoadBalancer;
import org.springframework.cloud.loadbalancer.core.ServiceInstanceListSupplier;
import reactor.core.publisher.Mono;

import java.util.List;
import java.util.Random;

public class CustomLoadBalancer implements ReactorServiceInstanceLoadBalancer {

    private final ServiceInstanceListSupplier serviceInstanceListSupplier;
    private final Random random = new Random();

    public CustomLoadBalancer(ServiceInstanceListSupplier serviceInstanceListSupplier) {
        this.serviceInstanceListSupplier = serviceInstanceListSupplier;
    }

    @Override
    public Mono<Response<ServiceInstance>> choose(Request request) {
        return serviceInstanceListSupplier.get()
                .next()
                .map(this::getRandomInstance);
    }

    private Response<ServiceInstance> getRandomInstance(List<ServiceInstance> instances) {
        if (instances.isEmpty()) {
            return new EmptyResponse();
        }
        ServiceInstance instance = instances.get(random.nextInt(instances.size()));
        return new DefaultResponse(instance);
    }
}
5.2 注册自定义策略
import org.springframework.cloud.loadbalancer.annotation.LoadBalancerClient;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

@Configuration
@LoadBalancerClient(name = "provider-service", configuration = CustomLoadBalancerConfig.class)
public class CustomLoadBalancerConfig {

    @Bean
    public ReactorServiceInstanceLoadBalancer customLoadBalancer(ServiceInstanceListSupplier supplier) {
        return new CustomLoadBalancer(supplier);
    }
}

六、负载均衡的测试

  1. 启动服务提供者实例
    • 分别运行两个服务实例,端口为 80818082
  2. 启动客户端服务
    • 启动带负载均衡配置的客户端。
  3. 测试负载均衡
    • 访问 http://localhost:8080/invokehttp://localhost:8080/invokeWebClient,观察服务响应是否轮流来自 80818082

七、负载均衡的优缺点

优点
  1. 性能提升:通过分发流量减轻单点负载压力。
  2. 容错性增强:服务实例宕机时,流量可分发至其他可用实例。
  3. 扩展性高:可动态添加或删除实例,支持水平扩展。
缺点
  1. 复杂性增加:需要额外的服务注册和发现机制。
  2. 一致性问题:客户端负载均衡可能导致分布式数据的一致性问题。
  3. 延迟:请求需要经过多次解析和路由,可能增加延迟。

八、总结

Spring Cloud 的负载均衡功能为微服务架构提供了高效的流量分发能力。无论是通过 RestTemplate 还是 WebClient,开发者都可以方便地实现客户端负载均衡。同时,Spring Cloud LoadBalancer 支持灵活的负载均衡策略,适应各种业务需求。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

Flying_Fish_Xuan

你的鼓励将是我创作最大的动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值