Spring Cloud Gateway 搭建与说明

目录

  1. Spring Cloud Gateway 搭建过程
    1. 配置Gateway
    2. 术语
    3. 工作原理
    4. 配置Route Predicate 和 Gateway Filter 工厂
    5. 配置路由规则
      1. 到达时间路由规则
      2. 时间区间路由规则
      3. Cookie路由规则
      4. 请求头路由规则
      5. 域名路由规则
      6. 请求类型路由规则
      7. 路径路由规则
      8. 请求参数路由
      9. 客户端IP地址路由规则
      10. 权重路由规则
    6. 请求响应装饰器(GatewayFilter)分类介绍与使用
      1. 添加请求头装饰器
      2. 请求参数装饰器
      3. 其他的装饰器配置
    7. 超时间配置
      1. 全局超时间配置
      2. 单路路由配置
    8. 开启容器的访问日志
    9. 网关支持的配置以及说明

Spring Cloud Gateway 搭建过程

Spring Cloud Gateway 是Spring Cloud 构建更新一代微服务网关的项目。和前一段的zuul相比,它的性能更好,配置也更加简单,扩展诸如权限校验、监控功能也更加方便。

Spring Cloud Gateway的特点:

  • Spring Cloud Gateway 是基于Spring Framework 5,Spring Boot2.0以及WebFlux反应式编程框架实现
  • 能够根据请求的属性做请求转发
  • 自由配置路由规则和过滤器
  • 集成熔断组件
  • 集成服务发现组件
  • 允许控制一段时间内的请求数量
  • 请求路径重写

配置Gateway

将Spring Cloud gateway加入到项目只需要在Spring Boot配置基础上引入spring-cloud-starter-gateway即可。完成的基于maven的依赖配置如下:

<?xml version="1.0" encoding="UTF-8"?>
 <project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
          xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 https://maven.apache.org/xsd/maven-4.0.0.xsd">
     <modelVersion>4.0.0</modelVersion>
     <parent>
         <groupId>org.springframework.boot</groupId>
         <artifactId>spring-boot-starter-parent</artifactId>
         <version>2.3.2.RELEASE</version>
         <relativePath/> <!-- lookup parent from repository -->
     </parent>
     <groupId>com.jackframe.practice.cloud</groupId>
     <artifactId>gateway</artifactId>
     <version>0.0.1-SNAPSHOT</version>
     <name>gateway</name>
     <description>Demo project for Spring Boot</description>

     <properties>
         <java.version>1.8</java.version>
         <spring-cloud.version>Hoxton.SR6</spring-cloud.version>
     </properties>

     <dependencies>
         <dependency>
             <groupId>org.springframework.cloud</groupId>
             <artifactId>spring-cloud-starter-gateway</artifactId>
         </dependency>
         <dependency>
             <groupId>org.springframework.cloud</groupId>
             <artifactId>spring-cloud-starter-netflix-eureka-client</artifactId>
         </dependency>

         <dependency>
             <groupId>org.springframework.boot</groupId>
             <artifactId>spring-boot-starter-actuator</artifactId>
         </dependency>
         <dependency>
             <groupId>org.springframework.cloud</groupId>
             <artifactId>spring-cloud-starter-netflix-hystrix</artifactId>
         </dependency>
         <dependency>
             <groupId>org.springframework.cloud</groupId>
             <artifactId>spring-cloud-config-client</artifactId>
         </dependency>
         <dependency>
             <groupId>org.springframework.boot</groupId>
             <artifactId>spring-boot-starter-test</artifactId>
             <scope>test</scope>
             <exclusions>
                 <exclusion>
                     <groupId>org.junit.vintage</groupId>
                     <artifactId>junit-vintage-engine</artifactId>
                 </exclusion>
             </exclusions>
         </dependency>
     </dependencies>

     <dependencyManagement>
         <dependencies>
             <dependency>
                 <groupId>org.springframework.cloud</groupId>
                 <artifactId>spring-cloud-dependencies</artifactId>
                 <version>${spring-cloud.version}</version>
                 <type>pom</type>
                 <scope>import</scope>
             </dependency>
         </dependencies>
     </dependencyManagement>

     <build>
         <plugins>
             <plugin>
                 <groupId>org.springframework.boot</groupId>
                 <artifactId>spring-boot-maven-plugin</artifactId>
             </plugin>
         </plugins>
     </build>

 </project>

项目基于Spring Cloud Hoxton.SR6 版本,引入Gateway(网关),eureka-client(eureka客户端,用于和Eureka注册中心通信,这里主要用于基于服务发现做请求路由),actuator(监控),hystrix(熔断),config-client(配置服务客户端-用于获取配置服务的配置信息),测试框架。

项目依赖参数配置:

bootstrap.yml

server:
  port: 9001 #服务端口
spring:
  profiles:
    active: profile1
  main:
    banner-mode: "off"
  application:
    name: api-gateway

bootstrap-profile1.yml:

spring:
  cloud:
    gateway:
      discovery:
        locator:
          enabled: true # 使用基于服务发现做请求路由
    config:
      discovery:
        enabled: true
        service-id: config-server
      profile: dev1
      username: account
      password: password
      name: api-gateway
  security:
    user:
      name: account
      password:password 
eureka:
  client:
    serviceUrl:
      defaultZone: http://account:password@left:8761/eureka/, http://account:password@center:8762/eureka/, http://account:password@right:8763/eureka/
    healthcheck:
      enabled: true

项目入口


@SpringBootApplication
@EnableDiscoveryClient
public class GatewayApplication {

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

}

术语

  • route(路由): route是网关项目的基础组成部分,由唯一的ID标志,一个具体的资源路径,一组能否路由的规则以及对请求和返回值做调整的过滤器组成。路由需要所有的路由规则都成立才能路由到具体的资源路径上。
  • Predicate(路由规则):Predicate其实就是Java 8 中 Funcation Predicate。Gateway可以识别固定配置,生成Predicate,对ServerWebExchange中的属性进行校验,如果校验通过则路由到指定的资源上,否则路由到预定义失败的资源上。
  • Filter(请求响应装饰器):是一种请求响应的切面应用,能够修改请求和响应数据。

工作原理

工作原理

Spring Cloud Gateway接收到一个请求后,Gateway Handler Mapping会去匹配一个route,然后交由Gateway Web Handler处理。Gateway Web Handler执行一串的Filter,之后交给代理服务。在到达代理服务前,请求经过的Filter都会执行结束;Gateway Web Handler获取到响应前,响应经过的Filter都执行完成。

配置Route Predicate 和 Gateway Filter 工厂

yml配置Route Predicate 和 Gateway Filter 支持简洁(shortcut)和完整两种配置方式。简洁配置中参数名称被Filter名称取代,值的分隔符“:”被“=”取代,后面紧跟具体的值。多个值用“,”隔离。完整配置严格按照{parameter}:{value}的格式编排。

简洁配置:

spring:
 cloud:
   gateway:
     routes:
     - id: after_route
       uri: https://example.org
       predicates:
       - Cookie=mycookie,mycookievalue

完整配置:

spring:
 cloud:
   gateway:
     routes:
     - id: after_route
       uri: https://example.org
       predicates:
       - name: Cookie
         args:
           name: mycookie
           regexp: mycookievalue

Cookie路由规则判定条件:请求中存在Cookie,并且Cookie中有参数mycookie,并且值等于mycookievalue。如果条件成立则路由到资源:https://example.org

以上是配置Cookie路由规则简介配置和完整配置的例子。Cookie路由规则配置需要2个参数,分别是路由名称(name)和路由名称所需参数(args),而Cookie路由规则的参数需要两个,分别是名称(name)和进行比较的值(regexp)。

简洁配置忽略了配置的参数,将所需的数据归拢到一行表达。

配置路由规则

Spring Cloud Gateway 内置了许多路由规则,分别根据HTTP请求中各种参数判定是否路由到指定资源。这些路由匹配规则是HandlerMapping结构的组成部分,允许同时配置多个路由规则。

到达时间路由规则

到达时间路由规则接收一个时间Java ZonedDateTime 格式时间,如果请求是在这个时间之后发生则路由到指定的资源上。以下是例子:

spring:
  cloud:
    gateway:
      routes:
      - id: after_route
        uri: https://example.org
        predicates:
        - After=2017-01-20T17:42:47.789-07:00[America/Denver]

时间区间路由规则

时间区间路由规则接收两个Java ZonedDateTime 格式时间的时间,如果请求在这两个时间中间发生,那么路由到指定的资源。以下是配置的例子

spring:
  cloud:
    gateway:
      routes:
      - id: between_route
        uri: https://example.org
        predicates:
        - Between=2017-01-20T17:42:47.789-07:00[America/Denver], 2017-01-21T17:42:47.789-07:00[America/Denver]

Cookie路由规则

Cookie路由规则需要提供名称(name)和符合Java正则表达式的比较规则(regexp)。Cookie路由规则会从请求的Cookie中获取配置名称对应的值,并校验该值是否符合配置的正则表达式。如果符合则路由到指定的资源上。以下是如果Cookie存在chocolate并且值为ch.p则路由到 https://example.org 的例子:

spring:
  cloud:
    gateway:
      routes:
      - id: cookie_route
        uri: https://example.org
        predicates:
        - Cookie=chocolate, ch.p

请求头路由规则

请求头路由规则和Cookie路由规则类似,只是请求头路由规则从请求的头部信息中获取指定的数据交给表达式校验。如果校验通过则路由到指定的资源。以下是如果header中的X-Request-Id是数字,则路由到 https://example.org 的例子:

spring:
  cloud:
    gateway:
      routes:
      - id: header_route
        uri: https://example.org
        predicates:
        - Header=X-Request-Id, \d+

域名路由规则

域名路由规则需要配置一份路由匹配规则,如果请求的域名符合匹配规则中的任一一项,那么路由到指定资源。匹配规则是Ant-Style格式。以下是配置如果请求任一somehost.org域名和子域名以及anotherhost.org和其子域名,那么路由到资源 https://example.org

请求类型路由规则

请求类型路由规则需要配置请求类型,请求类型路由根据请求中的请求类型路由到指定的资源。以下是如果请求是GET或者POST,那么路由到 https://example.org 的例子:

spring:
  cloud:
    gateway:
      routes:
      - id: method_route
        uri: https://example.org
        predicates:
        - Method=GET,POST`

路径路由规则

路径路由规则需要配置路径匹配规则,比如/red/{segment}。如果请求路径符合这个规则,请求则会路由到指定资源上。这个规则在Spring PathMatcher中定义。这里的segment变量定义在资源路径上。Spring Gateway痛殴ServerWebExchangeUtils.URITEMPLATEVARIABLESATTRIBUTE定义的变量,从ServerWebExchange.getAttributes()获取到的属性,提取出配置中所需的内容并以key-value的形式存储下来。后续的路由规则即可使从这个存储工具上获取到具体的值。一下是配置将路径/red/*以及/blue/*的请求路由到https://example.org 的例子:

spring:
  cloud:
    gateway:
      routes:
      - id: path_route
        uri: https://example.org
        predicates:
        - Path=/red/{segment},/blue/{segment}

请求参数路由

请求参数路需要配置一个属性名称的参数和可选的匹配规则。如果没有配置匹配规则,则只需要请求包含请求参数则路由到指定的资源;如果配置了匹配规则,则请求中包含配置的请求参数并且值符合匹配规则,那么路由到指定资源。以下是请求中包含参数green则路由到 https://example.org 的例子。

spring:
  cloud:
    gateway:
      routes:
      - id: query_route
        uri: https://example.org
        predicates:
        - Query=green

以下是请求中包含参数 green,并且值是符合正则表达式gree.(.表示匹配除"\r\n"之外的任何单个字符),比如green,greed的例子:

spring:
  cloud:
    gateway:
      routes:
      - id: query_route
        uri: https://example.org
        predicates:
        - Query=red, gree.

客户端IP地址路由规则

客户端IP地址路由规则需要配置IPv4或者IPv6的字符串,如果符合这个IP地址则路由到指定的资源上。比如配置192.168.1.1/24,那么192.168.1.1~192.168.1.24之间的IP地址都会被路由到指定的资源。以下是配置的例子:

spring:
  cloud:
    gateway:
      routes:
      - id: remoteaddr_route
        uri: https://example.org
        predicates:
        - RemoteAddr=192.168.1.1/24

权重路由规则

权重路由规则需要配置两个参数,分别是group和weight。group用来区分不同的权重配置,weight用来控制路由的占比。比如配置一个权重路由规则,group名称是group1,20%的请求路由到https://weightlow.org, 80%的请求路由到https://weighthigh.org 的配置例子如下:

spring:
  cloud:
    gateway:
      routes:
      - id: weight_high
        uri: https://weighthigh.org
        predicates:
        - Weight=group1, 8
      - id: weight_low
        uri: https://weightlow.org
        predicates:
        - Weight=group1, 2

请求响应装饰器(GatewayFilter)分类介绍与使用

GatewayFilter可以修改HTTP请求以及请求的响应上的特定位置的内容,比如请求参数和重写返回值内容,修改请求头内容等。

添加请求头装饰器

添加请求头装饰器需要配置两个参数,分别是请求内容的名称和对应的值,用于往符合条件的请求上添加请求头内容。另外还需要配置一个资源地址,用于配置需要做增加请求头内容的资源。配置的例子如下:

spring:
  cloud:
    gateway:
      routes:
      - id: add_request_header_route
        uri: https://example.org
        filters:
        - AddRequestHeader=X-Request-red, blue

ServerWebExchangeUtils.URITEMPLATEVARIABLESATTRIBUTE中配置的属性,请求响应装饰器也可以使用,使用方式和路径路由规则一样,比如:

spring:
  cloud:
    gateway:
      routes:
      - id: add_request_header_route
        uri: https://example.org
        predicates:
        - Path=/red/{segment}
        filters:
        - AddRequestHeader=X-Request-Red, Blue-{segment}

以上的如果是example.org的请求,那么往请求头中添加名称为X-Request-Red,内容为blue-(参数中segment对应的值)。

请求参数装饰器

请求参数装饰器和请求头类似,只是修改的是HTTP请求的请求参数内容。以下是配置请求参数装饰器的例子:

spring:
  cloud:
    gateway:
      routes:
      - id: add_request_parameter_route
        uri: https://example.org
        predicates:
        - Host: {segment}.myhost.org
        filters:
        - AddRequestParameter=foo, bar-{segment}

其他的装饰器配置

其他的配置都比较简单也很类似,可以直接查看官网文档

超时间配置

全局超时间配置

超时时间配置是指http连接超时和响应超时的配置。连接超时单位是毫秒,响应超时是Java.time.Duration对象,需要按照固定格式配置便于Spring Cloud 将其解析成为Java.time.Duration对象。

全局超时时间配置如下:

spring:
  cloud:
    gateway:
      httpclient:
        connect-timeout: 1000
        response-timeout: 5s

单路路由配置

Gateway允许给特定路由配置超时时间,配置如下:

- id: per_route_timeouts
  uri: https://example.org
  predicates:
    - name: Path
      args:
        pattern: /delay/{timeout}
  metadata:
    response-timeout: 200
    connect-timeout: 200

Java API配置例子如下:

import static org.springframework.cloud.gateway.support.RouteMetadataUtils.CONNECT_TIMEOUT_ATTR;
import static org.springframework.cloud.gateway.support.RouteMetadataUtils.RESPONSE_TIMEOUT_ATTR;

      @Bean
      public RouteLocator customRouteLocator(RouteLocatorBuilder routeBuilder){
         return routeBuilder.routes()
               .route("test1", r -> {
                  return r.host("*.somehost.org").and().path("/somepath")
                        .filters(f -> f.addRequestHeader("header1", "header-value-1"))
                        .uri("http://someuri")
                        .metadata(RESPONSE_TIMEOUT_ATTR, 200)
                        .metadata(CONNECT_TIMEOUT_ATTR, 200);
               })
               .build();
      }

开启容器的访问日志

容器访问日志开启可以在Runnable Jar启动命令后面跟上配置参数:-Dreactor.netty.http.server.accessLogEnabled=true。如果需要按照自定义日志文件,可以通过配置logback.xml实现。以下是配置的例子:

<appender name="accessLog" class="ch.qos.logback.core.FileAppender">
    <file>access_log.log</file>
    <encoder>
        <pattern>%msg%n</pattern>
    </encoder>
</appender>
<appender name="async" class="ch.qos.logback.classic.AsyncAppender">
    <appender-ref ref="accessLog" />
</appender>

<logger name="reactor.netty.http.server.AccessLog" level="INFO" additivity="false">
    <appender-ref ref="async"/>
</logger>

网关支持的配置以及说明

详见官网配置说明

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值