详解SpringCloud-gateway动态路由两种方式,以及路由加载过程

2021-03-07 08:30

阅读:593

标签:obj   shm   star   tput   字符串   plugins   des   snap   caching   

gateway配置路由主要有两种方式,一种是用yml配置文件,一种是写代码里,这两种方式都是不支持动态配置的。如:

技术图片
技术图片

下面就来看看gateway是如何加载这些配置信息的。

1 路由初始化

无论是yml还是代码,这些配置最终都是被封装到RouteDefinition对象中。

技术图片

一个RouteDefinition有个唯一的ID,如果不指定,就默认是UUID,多个RouteDefinition组成了gateway的路由系统。

所有路由信息在系统启动时就被加载装配好了,并存到了内存里。我们从源码来看看。

技术图片

圆圈里就是装配yml文件的,它返回的是PropertiesRouteDefinitionLocator,该类继承了RouteDefinitionLocator,RouteDefinitionLocator就是路由的装载器,里面只有一个方法,就是获取路由信息的。该接口有多个实现类,分别对应不同方式配置的路由方式。

技术图片
技术图片
技术图片

通过这几个实现类,再结合上面的AutoConfiguration里面的Primary信息,就知道加载配置信息的顺序。

PropertiesRouteDefinitionLocator-->|配置文件加载初始化| CompositeRouteDefinitionLocator RouteDefinitionRepository-->|存储器中加载初始化| CompositeRouteDefinitionLocator DiscoveryClientRouteDefinitionLocator-->|注册中心加载初始化| CompositeRouteDefinitionLocator

参考:https://www.jianshu.com/p/b02c7495eb5e

https://blog.csdn.net/X5fnncxzq4/article/details/80221488

技术图片

这是第一顺序,就是从CachingRouteLocator中获取路由信息,我们可以打开该类进行验证。

技术图片

不管发起什么请求,必然会走上面的断点处。请求一次,走一次。这是将路由信息缓存到了Map中。配置信息一旦请求过一次,就会被缓存到上图的CachingRouteLocator类中,再次发起请求后,会直接从map中读取。

如果想动态刷新配置信息,就需要发起一个RefreshRoutesEvent的事件,上图的cache会监听该事件,并重新拉取路由配置信息。

通过下图,可以看到如果没有RouteDefinitionRepository的实例,则默认用InMemoryRouteDefinitionRepository。而做动态路由的关键就在这里。即通过自定义的RouteDefinitionRepository类,来提供路由配置信息。

技术图片

例如:

技术图片

在getRouteDefinitions方法返回你自定义的路由配置信息即可。这里可以用数据库、nosql等等任意你喜欢的方式来提供。而且配置信息修改后,发起一次RefreshRoutesEvent事件即可让配置生效。这就是动态配置路由的核心所在,下面来看具体代码实现。

2 基于数据库、缓存的动态路由

pom.xml如下

?xml version="1.0" encoding="UTF-8"?>
="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 http://maven.apache.org/xsd/maven-4.0.0.xsd">
    >4.0.0/modelVersion>

    >com.maimeng/groupId>
    >apigateway/artifactId>
    >0.0.1-SNAPSHOT/version>
    >jar/packaging>

    >apigateway/name>
    >Demo project for Spring Boot/description>

    >
        >org.springframework.boot/groupId>
        >spring-boot-starter-parent/artifactId>
        >2.0.6.RELEASE/version>
        /> !-- lookup parent from repository -->
    /parent>

    >
        .build.sourceEncoding>UTF-8/project.build.sourceEncoding>
        .reporting.outputEncoding>UTF-8/project.reporting.outputEncoding>
        .version>1.8/java.version>
        -cloud.version>Finchley.SR1/spring-cloud.version>
    /properties>

    >
        >
            >org.springframework.cloud/groupId>
            >spring-cloud-starter-gateway/artifactId>
        /dependency>
        >
            >org.springframework.boot/groupId>
            >spring-boot-starter-webflux/artifactId>
        /dependency>
        >
            >org.springframework.boot/groupId>
            >spring-boot-starter-actuator/artifactId>
        /dependency>
        >
            >org.springframework.boot/groupId>
            >spring-boot-starter-data-redis/artifactId>
        /dependency>
        >
            >com.alibaba/groupId>
            >fastjson/artifactId>
            >1.2.51/version>
        /dependency


评论


亲,登录后才可以留言!