[springcloud microservices] Spring Cloud microservice gateway Gateway usage details

Table of contents

1. Introduction to Microservice Gateway

1.1 The role of the gateway

1.2 Common gateways

1.2.1 Traditional Gateway

1.2.2 Cloud Native Gateway

2. Gateway gateway introduction

2.1 Origin of the problem

2.2 Issues raised

2.2.1 Reinventing the wheel

2.2.2 Call inefficiency

2.2.3 Complex Refactoring

2.3 gateway improvement

3. Introduction to Spring Cloud Gateway

3.1 Gateway overview

3.2 Gateway features

3.3 Gateway core concept

3.3.1 Routing (route)

3.3.2 predicates 

3.3.3 Filter

3.4 Gateway working principle

4. Quick use of Gateway

4.1 Operation steps

4.1.1 Import maven dependencies

4.1.2 Add configuration file

4.1.3 Start the service and test

4.2 Integrate nacos

4.2.1 Introducing nacos dependencies

4.2.2 Modify configuration file

4.2.3 Effect Test

4.3 Integrate nacos automatic service discovery

5. Gateway routing assertion factory

5.1 Common routing assertion factories

5.1.1 Assertion factory based on Datetime type

5.1.2 Assertion factories based on remote addresses

5.1.3 Cookie-based assertion factory

5.1.4 Header-based assertion factory

5.1.5 Host-based assertion factory

5.1.6 Assertion factory based on Method request method

5.1.7 Assertion factory based on Path request path

5.1.8 Assertion factory based on Query request parameters

5.1.9 Assertion factory based on route weight

5.2 Routing assertion factory use

5.2.1 Time Assertions

5.2.2 header assertion

5.2.3 Query request parameter assertion

5.3 Custom route assertion factory

5.3.1 Custom routing assertion factory class

5.3.2 Configure custom classes to configuration files

5.3.3 Effect Test

 6. Gateway filter factory

6.1 Gateway filter use

6.1.1 Request header usage

6.1.2 Use of request header parameters

6.2 Custom Filter Factory

6.2.1 Custom filter class

6.2.2 Modify configuration file

6.2.3 Interface Test

6.3 Global Filters

6.3.1 Overview

6.3.2 Global filter classification

6.3.3 Global filter usage

6.3.4 Interface Test

7. Gateway cross-domain settings

 7.1 Operation process

7.1.1 Modify configuration file

Eight, written at the end of the text


1. Introduction to Microservice Gateway

In a mature and stable microservice architecture, in order to protect the security of the back-end interface and avoid exposing the real interface address, usually before the request reaches the interface, it will go through a layer of service called "gateway", proxy and forward through the gateway, and then To the backend, that's what the gateway does. For example, familiar nginx, gateway, zuul, etc. can be said to be used in the products of Internet companies. What are the functions of gateways?

1.1 The role of the gateway

It can be said that the gateway plays a very important role in a system:

  • Hide the real API address from the outside world to protect the security of API resources;
  • Identify and intercept malicious requests, filter and audit requests in advance;
  • The bearer traffic entrance forwards the requested traffic according to the system load;

1.2 Common gateways

As the microservice architecture becomes more and more common, gateways play an increasingly important role in the rectification architecture. With the rise of cloud native and large-scale implementation, various new types of gateways have gradually begun to appear.

1.2.1 Traditional Gateway

Under the springcloud microservice system, traditional gateways can still be considered, as follows:

  • nginx;
  • zul;
  • gateway;

1.2.2 Cloud Native Gateway

With the large-scale application of k8s, some related gateways have also begun to appear, such as:

  • ingress;
  • istio(envoy);
  • api gateway;
  • kong;
  • apisix...

2. Gateway gateway introduction

2.1 Origin of the problem

In the microservice architecture, a system is split into many microservices. So how to call so many microservices as a client? If there is no gateway, we can only record the address of each microservice on the client and use it separately.

2.2 Issues raised

There are many problems with the above structure:

2.2.1 Reinventing the wheel

Each business needs to carry out logic such as authentication, current limiting, authority verification, cross-domain, etc. independently, and each business is fighting on its own, making its own wheels to achieve it;

2.2.2 Call inefficiency

If the business volume is relatively simple, there will be no problem for the time being. As the business becomes more and more complex, a complex page may involve hundreds of microservices working together. If each microservice is assigned a domain name, On the one hand, the client code will be difficult to maintain, involving hundreds of domain names. On the other hand, it is the bottleneck of the number of connections. Imagine that you open an app and find that hundreds of remote calls are involved through packet capture. would be very inefficient;

2.2.3 Complex Refactoring

If you need to refactor microservices in the later stage, it will also become very troublesome. You need the client to cooperate with you in the transformation, such as commodity services. As the business becomes more and more complex, it needs to be split into multiple microservices later. Services, at this time, the services provided to the outside world also need to be split into multiple parts, and at the same time, the client needs to cooperate with you in the transformation, which is very painful;

2.3 gateway improvement

For the above problems, API gateway can be used to solve them

The so-called API gateway refers to the unified entrance of the system. It encapsulates the internal structure of the application program and provides unified services for the client. Some public logic that has nothing to do with the functions of the business itself can be implemented here, such as authentication, authentication, monitoring, and routing. Retweet and more.

After adding the API gateway, the architecture diagram of the system becomes as follows

3. Introduction to Spring Cloud Gateway

3.1 Gateway overview

  • It is the second-generation gateway framework officially launched by Spring Cloud, positioned to replace Netflix Zuul1.0. Compared with Zuul, Spring Cloud Gateway provides better performance and more powerful functions;
  • It is a responsive API gateway implemented by WebFlux + Netty + Reactor. It doesn't work in a traditional servlet container, nor can it be built into a war package;
  • It aims to provide a simple and effective API routing management method for the microservice architecture, and provide the basic functions of the gateway based on the Filter method, such as security authentication, monitoring, current limiting, etc.;

3.2 Gateway features

Compared with the first generation gateway zuul, Gateway provides rich and powerful functions;

1) Build based on Spring Framework 5, Project Reactor and Spring Boot 2.0;

2) Dynamic routing: able to match any request attribute;

3) Support path rewriting;

4) Integrate Spring Cloud service discovery function (Nacos, Eureka);

5) Flow control downgrade function (Sentinel, Hystrix) can be integrated;

6) You can specify easy-to-write Predicate (assertion) and Filter (filter) for routing;

3.3 Gateway core concept

3.3.1  Routing (route)

Routing is the most basic part of a gateway. Routing information includes an ID, a destination URI, a set of assertion factories, and a set of Filters. If the assertion is true, the requested URL matches the configured route.

3.3.2  predicates 

The assertion function in Java8, the assertion function type in SpringCloud Gateway is ServerWebExchange in the Spring5.0 framework. The assertion function allows developers to define any information that matches the Http request, such as request headers and parameters.

3.3.3 Filter

The filters in SpringCloud Gateway are divided into Gateway FilIer and Global Filter. Filter can process requests and responses.

3.4 Gateway working principle

According to the above figure, the workflow of the gateway is roughly as follows:

  • Gateway Client sends a request to Gateway Server;
  • The request will first be extracted and assembled into a gateway context by the HttpWebHandlerAdapter;
  • Then the context of the gateway will be passed to DispatcherHandler, which is responsible for dispatching the request to RoutePredicateHandlerMapping;
  • RoutePredicateHandlerMapping is responsible for route lookup, and judges whether the route is available according to the route assertion;
  • If the assertion succeeds, the filter chain is created and called by FilteringWebHandler;
  • The request will go through the PreFilter--microservice--PostFilter method once, and finally return the response;

4. Quick use of Gateway

Next, quickly experience the use of gateway through a case

4.1 Operation steps

4.1.1 Import maven dependencies

To create a new project, you only need to import this dependency

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

4.1.2 Add configuration file

Refer to the comments in the configuration file for understanding. The core of the gateway function lies in the use of the configuration file, which can flexibly control routing through declarative configuration;


server:
  port: 8088

spring:
  application:
    name: api-gateway
  cloud:
    gateway:
      routes:
        #当前路由的唯一标识,路由到哪个服务上面去
        - id: order-route
          uri: http://localhost:8083
          predicates:
            #即所有以order-serv开头的请求都转发到这个微服务处理
            - Path=/order-serv/**
          filters:
            #访问的时候,Gateway会自动的把order-serv过滤掉,从而转发到对应微服务的正确路径上
            #比如客户端访问的是 http://localhost:8088/order-serv/order/add,通过gateway之后实际访问的是http://localhost:8088/order/add
            - StripPrefix=1

4.1.3 Start the service and test

@SpringBootApplication
public class GatewayApp01 {

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

Before starting the order module and stock module, there is an /order/add interface in the order module. According to the above configuration, our access needs to be forwarded by the gateway, so the complete request address is: http://localhost:8088/ order -serv/order/add , if accessing this address can have the same effect as accessing: http://localhost:8083/order/add  , it means that the configuration of the gateway has taken effect, and the effect of the browser access interface is as follows:

4.2 Integrate nacos

In the above configuration file, it can be found that the address of the gateway forwarding path is directly written in the configuration file. This method is not standardized and will cause many problems. The correct and reasonable way is to forward through the specified service name. Next, use nacos as the registration center to obtain this address from the registration center;

4.2.1 Introducing nacos dependencies

       <dependency>
            <groupId>com.alibaba.cloud</groupId>
            <artifactId>spring-cloud-starter-alibaba-nacos-discovery</artifactId>
        </dependency>

4.2.2 Modify configuration file

There are two main points, one is to add the address of nacos, but to change the forwarded uri address to the service name on nacos


server:
  port: 8088

spring:
  application:
    name: api-gateway

  # nacos注册中心地址
  cloud:
    nacos:
      discovery:
        server-addr: localhost:8848 #服务注册中心地址

    gateway:
      routes:
        #当前路由的唯一标识,路由到哪个服务上面去
        - id: order-route
          uri: lb://order-service #需要转发的服务地址,nacos上注册的那个服务地址
          predicates:
            #即所有以order-serv开头的请求都转发到这个微服务处理
            - Path=/order-serv/**
          filters:
            #访问的时候,Gateway会自动的把pay过滤掉,从而转发到对应微服务的正确路径上
            #比如客户端访问的是 http://localhost:8088/order-serv/order/add,实际访问的是http://localhost:8088/order/add
            - StripPrefix=1

4.2.3 Effect Test

After starting the services of several modules, call the same interface again, which is consistent with the above effect

4.3 Integrate nacos automatic service discovery

Based on the integration of nacos, the configuration file of the gateway can be further simplified as follows. Through this configuration, when the request address is: /order-service/order/add interface, it will automatically go to nacos to find out whether there is such a service exist;


server:
  port: 8088

spring:
  application:
    name: api-gateway

  # nacos注册中心地址
  cloud:
    nacos:
      discovery:
        server-addr: localhost:8848 #服务注册中心地址

    gateway:
      discovery:
        locator:
          enabled: true #是否启动自动发现nacos上面的服务

After starting the service and testing again, the correct return result can still be obtained;

5. Gateway routing assertion factory

Gateway provides the configuration of the routing assertion factory, which makes the processing of requests richer and more flexible. Developers only need to set some rules in the configuration file according to the business scenario. Spring Cloud Gateway includes a number of built-in assertion factories, all of which match different attributes of HTTP requests, as follows:

5.1 Common routing assertion factories

5.1.1  Assertion factory based on Datetime type

This type of assertion is judged based on time, and there are three main types:

  • AfterRoutePredicateFactory: Receive a date parameter to determine whether the requested date is later than the specified date;
  • BeforeRoutePredicateFactory: Receive a date parameter to determine whether the requested date is earlier than the specified date;
  • BetweenRoutePredicateFactory: Receive two date parameters to determine whether the requested date is within the specified time period

 ‐ After=2022‐12‐29T23:59:59.789+08:00[Asia/Shanghai]

5.1.2 Assertion factories based on remote addresses

RemoteAddrRoutePredicateFactory: Receive an IP address segment and determine whether the requesting host address is in the address segment

 ‐ RemoteAddr=192.168.1.1/24

5.1.3 Cookie-based assertion factory

CookieRoutePredicateFactory: Receives two parameters, the cookie name and a regular expression. Determine if the request cookie has the given name and the value matches the regular expression

‐Cookie=china, ch

5.1.4 Header-based assertion factory

HeaderRoutePredicateFactory: Receives two parameters, header name and regular expression. Determine whether the request header has the given name and the value matches the regular expression

‐Header=X‐Request‐Id, \d+

5.1.5 Host-based assertion factory

HostRoutePredicateFactory: Receives one parameter, the host name pattern. Determine whether the requested Host meets the matching rules

‐Host=**.testhost.org

5.1.6 Assertion factory based on Method request method

MethodRoutePredicateFactory: Receive a parameter to determine whether the request type matches the specified type

Method = GET

5.1.7 Assertion factory based on Path request path

PathRoutePredicateFactory: Receive a parameter to determine whether the URI part of the request satisfies the path rules

‐Path=/foo/{segment}

5.1.8 Assertion factory based on Query request parameters

QueryRoutePredicateFactory : Receive two parameters, request param and regular expression, determine whether the request parameter has the given name and the value matches the regular expression

‐Query=baz, ba.

5.1.9 Assertion factory based on route weight

WeightRoutePredicateFactory: Receive a [group name, weight], and then forward the routes in the same group according to the weight

routes:
 ‐id: weight_route1
  uri: host1
  predicates:
 ‐Path=/product/**
 ‐Weight=group3, 1
 ‐id: weight_route2
  uri: host2
  predicates:
 ‐Path=/product/**
 ‐Weight= group3, 9

5.2 Routing assertion factory use

5.2.1 Time Assertions

Add the following configuration file, which means that under the premise of satisfying the routing and forwarding rules, the time needs to be after the configured time;


server:
  port: 8088

spring:
  application:
    name: api-gateway

  # nacos注册中心地址
  cloud:
    nacos:
      discovery:
        server-addr: localhost:8848

    gateway:
      routes:
        - id: order-route
          uri: lb://order-service
          predicates:
            - Path=/order/**
            - After=2022-12-29T23:59:59.789+08:00[Asia/Shanghai]

Start again and access the interface, see the following effect

5.2.2 header assertion

Add the following configuration, which means that the request header also needs to carry a parameter whose key is username and value is jerry


server:
  port: 8088

spring:
  application:
    name: api-gateway

  # nacos注册中心地址
  cloud:
    nacos:
      discovery:
        server-addr: localhost:8848

    gateway:
      routes:
        - id: order-route
          uri: lb://order-service
          predicates:
            - Path=/order/**
            - After=2022-12-29T23:59:59.789+08:00[Asia/Shanghai]
            - Header=username,jerry

Initiate a request through postman, you can see the following effect

If the parameters in the header are removed or written incorrectly, 404 will appear;

5.2.3 Query request parameter assertion

Add the following configuration, that is, the request must carry the name parameter

server:
  port: 8088

spring:
  application:
    name: api-gateway

  # nacos注册中心地址
  cloud:
    nacos:
      discovery:
        server-addr: localhost:8848

    gateway:
      routes:
        - id: order-route
          uri: lb://order-service
          predicates:
            - Path=/order/**
            - After=2022-12-29T23:59:59.789+08:00[Asia/Shanghai]
            #- Header=username,jerry
            - Query=name

Request the interface again, if you do not carry the name, you will see the request 404

after carrying name

5.3 Custom route assertion factory

If the built-in routing assertion factory still cannot meet your individual needs, you can consider customizing the routing assertion factory.

The custom routing assertion factory needs to inherit the AbstractRoutePredicateFactory class and rewrite the logic of the apply method. In the apply method, you can get the ServerHttpRequest object through exchange.getRequest(), so that you can get the requested parameters, request method, request header and other information.

Points to note for custom routing assertion factories:

  • Must be a spring component bean;
  •  The class must end with RoutePredicateFactory;
  • AbstractRoutePredicateFactory must be inherited;
  •  A static inner class must be declared, and properties must be declared to receive the information of the corresponding assertion in the configuration file;
  • It needs to be bound with shortcutFieldOrder;
  • Make a logical judgment through apply, true means the match is successful, and false means the match fails;

5.3.1 Custom routing assertion factory class

@Component
public class CheckAuthRoutePredicateFactory extends AbstractRoutePredicateFactory<CheckAuthRoutePredicateFactory.Config> {

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

    public List<String> shortcutFieldOrder() {
        return Arrays.asList("name");
    }

    public Predicate<ServerWebExchange> apply(CheckAuthRoutePredicateFactory.Config config) {
        return new GatewayPredicate() {
            public boolean test(ServerWebExchange exchange) {
                if(config.getName().equals("hello")){
                    return true;
                }
                return false;
            }
        };
    }

    //接受配置文件中中的参数
    @Validated
    @Data
    public static class Config {

        private String name;

    }
}

5.3.2 Configure custom classes to configuration files

5.3.3 Effect Test

After starting the related module service, call the interface again, and you can see the following effect

The above shows that the parameters in the configuration file can be routed normally after matching the assertion factory. If the parameters in the configuration file are modified

 

Test the interface again, you can see the following effect

 6. Gateway filter factory

From the execution flow chart of gateway at the beginning of the article, we can see that Gateway has many built-in filter factories. We can perform some business logic processors through some filter factories, such as adding and removing response headers, adding and removing parameters, etc., and gateway filtering Detailed description of the filter: gateway filter description

The existence and use of filters can control the source requests more carefully, so as to achieve the purpose of protecting the server interface resources.

6.1 Gateway filter use

6.1.1 Request header usage

Function: Add Header for the original request, corresponding filter factory: AddRequestHeader, modify the configuration file


server:
  port: 8088

spring:
  application:
    name: api-gateway

  # nacos注册中心地址
  cloud:
    nacos:
      discovery:
        server-addr: localhost:8848

    gateway:
      routes:
        - id: order-route
          uri: lb://order-service
          predicates:
            - Path=/order/**
            - After=2022-12-29T23:59:59.789+08:00[Asia/Shanghai]
            #- Header=username,jerry
            #- Query=name
            #- CheckAuth=jerry
          filters:
            - AddRequestHeader=X-Request-color,red

Add the following test interface to OrderController

    @GetMapping("/header")
    public String header(@RequestHeader("X-Request-color") String color){
        return color;
    }

Browser request interface, you can see the following effect, indicating that the request forwarded from the gateway has the parameter red;

6.1.2 Use of request header parameters

Add the following configuration parameters

Add a test interface to OrderController

    @GetMapping("/request-param")
    public String testRequestParam(@RequestParam("color")String color) throws Exception {
        logger.info("获取请求参数:" + color);
        return color;
    }

Test the interface, you can see the following effects

6.2 Since

6.2 Custom Filter Factory

In some cases, if the built-in gateway filter does not meet the requirements, you can consider custom filters, which are relatively simple to use, custom classes, and inherit AbstractNameValueGatewayFilterFactory, and the custom class name must end with GatewayFilterFactory and Hand over to spring management;

6.2.1 Custom filter class

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

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

    public List<String> shortcutFieldOrder() {
        return Arrays.asList("name");
    }

    public GatewayFilter apply(CheckAuthGatewayFilterFactory.Config config) {
        return (exchange, chain) -> {
            String paramValue = exchange.getRequest().getQueryParams().getFirst("name");
            if (StringUtils.isNotEmpty(paramValue) && paramValue.equals("jerry")) {
                return chain.filter(exchange);
            } else {
                exchange.getResponse().setStatusCode(HttpStatus.NOT_FOUND);
                return  exchange.getResponse().setComplete();
            }
            
        };
    }

    @Data
    public static class Config {
        private String name;
    }
}

6.2.2 Modify configuration file

6.2.3 Interface Test

Start the related module service, call the /order/add interface through the gateway, if the name parameter is passed in and the value is correct

 If the value is incorrect, the following effect will appear

6.3 Global Filters

The above filters can be considered as partial filters according to the classification. The local filter needs to be configured in the route for a certain route. However, if there are many routes that need to be controlled in the actual business, it is necessary to write a lot of local filters. Filters, especially those scenes that have the same need to be filtered, are redundant. At this time, you can consider using global filters

6.3.1 Overview

For all routing requests, once defined, it will take effect globally. The GlobalFilter interface has the same interface definition as GatewayFilter, but GlobalFilter will act on all routes.

6.3.2 Global filter classification

The following lists the official and commonly used gateway global filters

6.3.3 Global filter usage

Customize a class to implement the GlobalFilter interface

@Component
@Slf4j
public class LogFilter implements GlobalFilter {

    @Override
    public Mono<Void> filter(ServerWebExchange exchange, GatewayFilterChain chain) {
        log.info(exchange.getRequest().getPath().value());
        return chain.filter(exchange);
    }
}

6.3.4 Interface Test

After starting the relevant module services, access the above interface, you can see that the console outputs the requested path information;

7. Gateway cross-domain settings

The concept of crossing is familiar to many students. There are many solutions to cross domains. For example, setting in nginx is a relatively common one. Gateway also provides solutions to cross domains.

è¿éæå¥å¾çæè¿°

 7.1 Operation process

Official document: gateway cross-domain configuration manual

7.1.1 Modify configuration file

Add cross-domain related configuration information

server:
  port: 8088

spring:
  application:
    name: api-gateway

  # nacos注册中心地址
  cloud:
    nacos:
      discovery:
        server-addr: localhost:8848

    gateway:
      # ----------- 跨域相关的配置
      globalcors:
        cors-configurations:
          '[/**]':  #拦截的请求
            allowedOrigins: #允许跨域的请求来源
              - "http://localhost:8080"
            allowedMethods: #运行跨域的请求方式
              - "GET"
              - "POST"
      routes:
        - id: order-route
          uri: lb://order-service
          predicates:
            - Path=/order/**
            - After=2022-12-29T23:59:59.789+08:00[Asia/Shanghai]
            #- Header=username,jerry
            #- Query=name
            #- CheckAuth=jerry
          filters:
            #- AddRequestHeader=X-Request-color,red
            #- AddRequestParameter=color,blue
            - CheckAuth=name,jerry

Eight, written at the end of the text

This article explains the use of gateway in detail in a large space. For more information about the use of gateway, you can refer to the official website documents for learning, such as using gateway for unified authentication, current limiting, etc., as an excellent programmable service gateway , it is necessary to study and understand it in depth before it can be used reasonably in the design of the architecture.

Guess you like

Origin blog.csdn.net/congge_study/article/details/129892885