spring cloud gateway 的配置

Spring Cloud Gateway 是一个基于 Spring Framework 的网关解决方案,用于管理和路由微服务请求。它提供了动态路由、负载均衡、路径重写、过滤请求、限流等功能。以下是 Spring Cloud Gateway 的基本配置方法,包括路由、过滤器和限流等。

1. 基本依赖配置

在项目的 pom.xml 文件中添加 Spring Cloud Gateway 的依赖:

<dependency>
    <groupId>org.springframework.cloud</groupId>
    <artifactId>spring-cloud-starter-gateway</artifactId>
</dependency>
<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-actuator</artifactId>
</dependency>

2. 基本的路由配置

可以在 application.yml 文件中使用静态配置,也可以使用 Java 代码配置。以下是静态配置示例:

spring:
  cloud:
    gateway:
      routes:
        - id: service_route_1
          uri: http://localhost:8081
          predicates:
            - Path=/service1/**
          filters:
            - RewritePath=/service1/(?<segment>.*), /$\\{segment}

        - id: service_route_2
          uri: lb://SERVICE-2
          predicates:
            - Path=/service2/**
          filters:
            - RemoveRequestHeader=Cookie

解析

  • id: 每个路由的唯一标识。
  • uri: 路由目标的 URI,可以是具体 URL(如 http://localhost:8081)或服务名(如 lb://SERVICE-2)。
  • predicates: 路由断言,控制请求是否符合路由条件。例如 Path 断言指定路径 /service1/** 的请求才能通过此路由。
  • filters: 过滤器,可用来修改请求/响应,比如 RewritePath 用来重写路径,RemoveRequestHeader 用于删除请求头。

3. 动态路由配置(Java 代码方式)

通过 RouteLocator 定义自定义路由:

import org.springframework.cloud.gateway.route.RouteLocator;
import org.springframework.cloud.gateway.route.builder.RouteLocatorBuilder;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

@Configuration
public class GatewayConfig {

    @Bean
    public RouteLocator customRouteLocator(RouteLocatorBuilder builder) {
        return builder.routes()
            .route("path_route", r -> r.path("/service1/**")
                .filters(f -> f.rewritePath("/service1/(?<segment>.*)", "/${segment}"))
                .uri("http://localhost:8081"))
            .route("lb_route", r -> r.path("/service2/**")
                .filters(f -> f.addRequestHeader("X-Request-Id", "my-custom-header"))
                .uri("lb://SERVICE-2"))
            .build();
    }
}

4. 常见过滤器配置

Spring Cloud Gateway 内置了多种过滤器,以下是常用过滤器的配置方式:

  • AddRequestHeader:向请求添加一个自定义的请求头。

    filters:
      - AddRequestHeader=X-Request-Id, 123
    
  • AddRequestParameter:向请求添加一个参数。

    filters:
      - AddRequestParameter=lang, en
    
  • RewritePath:重写请求路径。

    filters:
      - RewritePath=/service/(?<segment>.*), /$\\{segment}
    
  • StripPrefix:删除路径的前缀。

    filters:
      - StripPrefix=1
    
  • Retry:重试配置,适用于调用失败后自动重试。

    filters:
      - name: Retry
        args:
          retries: 3
          statuses: BAD_GATEWAY
    

5. 限流配置(Rate Limiter)

使用令牌桶算法对请求进行限流,通常使用 redis-rate-limiter

  • 引入 Redis 依赖(如果使用 Redis 作为限流器存储):

    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-data-redis-reactive</artifactId>
    </dependency>
    
  • 配置限流器:

    spring:
      cloud:
        gateway:
          routes:
            - id: rate_limited_route
              uri: lb://SERVICE-3
              predicates:
                - Path=/rate-limit/**
              filters:
                - name: RequestRateLimiter
                  args:
                    redis-rate-limiter.replenishRate: 10  # 每秒产生 10 个令牌
                    redis-rate-limiter.burstCapacity: 20  # 最大桶容量为 20
    

6. 负载均衡配置

Spring Cloud Gateway 支持负载均衡,可以直接通过 lb:// 指向注册在 Eureka 或 Consul 中的服务。例如:

spring:
  cloud:
    gateway:
      routes:
        - id: load_balanced_route
          uri: lb://SERVICE-4
          predicates:
            - Path=/load-balance/**

7. 故障处理与熔断器配置(Hystrix)

可以配置熔断器来处理超时或服务不可用的情况:

spring:
  cloud:
    gateway:
      routes:
        - id: hystrix_route
          uri: lb://SERVICE-5
          predicates:
            - Path=/circuit-breaker/**
          filters:
            - name: CircuitBreaker
              args:
                name: myCircuitBreaker
                fallbackUri: forward:/fallback

8. 自定义过滤器

实现 GatewayFilter 接口来自定义过滤器,用于实现更加复杂的业务逻辑。例如,自定义日志记录、身份验证等:

import org.springframework.cloud.gateway.filter.GatewayFilter;
import org.springframework.cloud.gateway.filter.GatewayFilterChain;
import org.springframework.cloud.gateway.filter.factory.AbstractGatewayFilterFactory;
import org.springframework.http.server.reactive.ServerHttpRequest;
import org.springframework.stereotype.Component;
import org.springframework.web.server.ServerWebExchange;
import reactor.core.publisher.Mono;

@Component
public class CustomLoggingFilter extends AbstractGatewayFilterFactory<CustomLoggingFilter.Config> {

    public static class Config {
        // 配置属性可以在此定义
    }

    public CustomLoggingFilter() {
        super(Config.class);
    }

    @Override
    public GatewayFilter apply(Config config) {
        return (exchange, chain) -> {
            ServerHttpRequest request = exchange.getRequest();
            System.out.println("Custom logging filter: " + request.getURI());
            return chain.filter(exchange);
        };
    }
}

9. 全局过滤器

全局过滤器会应用于所有请求,可以实现 GlobalFilter 接口:

import org.springframework.cloud.gateway.filter.GlobalFilter;
import org.springframework.core.Ordered;
import org.springframework.stereotype.Component;
import org.springframework.web.server.ServerWebExchange;
import reactor.core.publisher.Mono;

@Component
public class LoggingGlobalFilter implements GlobalFilter, Ordered {

    @Override
    public Mono<Void> filter(ServerWebExchange exchange, GatewayFilterChain chain) {
        System.out.println("Global Filter executed for request: " + exchange.getRequest().getURI());
        return chain.filter(exchange);
    }

    @Override
    public int getOrder() {
        return -1; // 设置过滤器的优先级
    }
}

10. 运行监控

Spring Cloud Gateway 可以通过 Actuator 提供的 /actuator/gateway/routes 端点监控路由状态和其他信息,确保在生产环境中可以对网关配置进行有效的监控和管理。

总结

Spring Cloud Gateway 配置灵活多样,可以通过配置文件、Java 代码定义静态或动态路由,支持负载均衡、限流和熔断器等功能,满足微服务架构下的 API 网关需求。


Spring Cloud Gateway 的配置示例中,我们通过 routes 配置不同的路由规则,每个路由包含 iduripredicatesfilters 等配置项。这些配置项共同决定了请求如何从网关路由到目标服务。

配置项解析

spring:
  cloud:
    gateway:
      routes:
        - id: service_route_1
          uri: http://localhost:8081
          predicates:
            - Path=/service1/**
          filters:
            - RewritePath=/service1/(?<segment>.*), /$\\{segment}

        - id: service_route_2
          uri: lb://SERVICE-2
          predicates:
            - Path=/service2/**
          filters:
            - RemoveRequestHeader=Cookie

1. id

  • id: 每个路由的唯一标识,用于在系统中区分不同的路由。
  • 示例中的 service_route_1service_route_2 分别是两个不同路由的 ID。这个 ID 可以用于监控、调试,或管理特定路由规则。

2. uri

  • uri: 路由的目标 URI,可以是具体的 URL,也可以是服务名称。
    • http://localhost:8081:直接指定目标服务的地址。请求符合路由规则时会被转发到 localhost:8081 上的服务。
    • lb://SERVICE-2:表示使用 Spring Cloud 的负载均衡机制,将请求转发到服务注册中心中名称为 SERVICE-2 的服务实例上。

注意:当 urilb:// 为前缀时,表示使用负载均衡,适合动态获取多个实例。

3. predicates

  • predicates: 路由断言,用于判断请求是否符合此路由规则。符合条件的请求会被转发到对应的 URI。
  • Path=/service1/**:这是 Path 断言,用于匹配请求路径。如果请求路径匹配 /service1/**(如 /service1/order/123),则符合此路由条件。/service1/** 表示 /service1/ 后面可以跟任意路径。
  • Path=/service2/**:同样是 Path 断言,用于匹配路径 /service2/** 的请求。

Spring Cloud Gateway 中,断言类型丰富,包括 PathMethodHeader 等,具体的组合可以实现复杂的路由需求。

4. filters

  • filters: 路由过滤器,用于在请求进入目标服务之前或响应返回客户端之前,修改请求或响应的内容。过滤器可以重写路径、移除请求头、添加请求参数等操作。
RewritePath
  • 作用RewritePath 用于对路径进行重写。
  • 格式RewritePath=/<oldPath>/regex, /<newPath>/replacement
  • 示例RewritePath=/service1/(?<segment>.*), /$\\{segment}
    • service1/(?<segment>.*):匹配请求路径中的 /service1/ 后面部分,并将匹配部分命名为 segment
    • /$\\{segment}:将 segment 中的内容替换到新路径中,从而实现路径的重写。
    • 效果:请求路径 /service1/order/123 将被重写为 /order/123,即去掉了 /service1 前缀。
RemoveRequestHeader
  • 作用RemoveRequestHeader 用于删除指定的请求头。
  • 格式RemoveRequestHeader=<headerName>
  • 示例RemoveRequestHeader=Cookie
    • 表示从请求中移除 Cookie 请求头,通常用于避免将敏感信息传递到后端服务,或在负载均衡场景下减少无关请求头。
    • 效果:当请求符合 service_route_2 路由条件时,会移除 Cookie 头,确保目标服务 SERVICE-2 不会收到客户端的 Cookie 信息。

配置示例总结

  • service_route_1:将请求路径匹配为 /service1/** 的请求重写为去掉前缀 /service1 的路径,再转发到 localhost:8081
  • service_route_2:将路径为 /service2/** 的请求移除 Cookie 请求头后,通过负载均衡方式转发到 SERVICE-2 服务。

示例请求匹配流程

  1. 匹配 service_route_1 路由

    • 假设请求路径为 /service1/order/123
    • 断言 Path=/service1/** 生效,符合此路由。
    • RewritePath 过滤器生效,将路径重写为 /order/123
    • 请求被转发到 http://localhost:8081/order/123
  2. 匹配 service_route_2 路由

    • 假设请求路径为 /service2/customer/456,并且包含 Cookie 请求头。
    • 断言 Path=/service2/** 生效,符合此路由。
    • RemoveRequestHeader=Cookie 过滤器生效,将 Cookie 请求头移除。
    • 请求被转发到 SERVICE-2 服务中的某个实例,路径为 /customer/456

小结

  • Spring Cloud Gateway 中的每个路由都由 id 唯一标识。
  • uri 指定目标服务的地址,可以是静态的 URL 或通过 lb:// 表示的负载均衡地址。
  • predicates 指定请求条件,只有符合的请求才会进入此路由。
  • filters 可以对符合路由条件的请求或响应进行处理,例如路径重写、删除请求头等。
posted @ 2024-10-28 22:52  gongchengship  阅读(154)  评论(0编辑  收藏  举报