一、前言
网关作为整个微服务集群的入口,承担着对外部请求的认证和鉴权职责,同时作为网关,相关配置的频繁变动是必然的,这就要求网关具备高度的灵活性,不能每次配置变动都需要重启网关来实现配置加载。基于以上实际场景,本文引出接下来要介绍的重点——网关节点动态加载网关配置,基本原理是基于nacos
的配置中心和Spring
容器的事件发布监听机制,配置中心的网关配置变动后,触法配置变动事件,gateway
重新加载配置到运行内存中。
二、Nacos配置
如下图所示,不同环境创建不同的命名空间。
这里需要注意的是,这里文件的名字需要和不同环境里配置的dataId
的值保持一致,否则会加载失败。
本文使用以下可能在服务运行期间会发生变动的应用配置:
## 不需要认证的请求
auth.skip.urls=[/login]
## jwt生成key使用到的秘钥
jwt.secret.key=q3t6w9z$C&F)J@NcQfTjWnZr4u7x
## jwt的token过期时间
jwt.refresh.token.expireTime=1000
三、代码实现
网关集成动态加载配置需要基于Spring
容器的事件发布监听机制,配置更改事件发布后,触发RouteDefinitionWriter
更新内存中的配置值。其中RouteDefinitionWriter
的默认实现为InMemoryRouteDefinitionRepository
,该类的功能是持有网关运行期间使用到的各种应用配置,其底层数据结构是一个HashMap
,属性名为key
,RouteDefinition
为包装了属性值的Bean
,在下文中将详细介绍如何实现动态配置加载。
首选,需要定义属性配置类及相关配置:
@Data
@ConfigurationProperties(prefix="nacos")
@Configuration
public class NacosGatewayProperties {
private String address;
private String dataId;
private String groupId;
private Long timeout;
}
配置值如下所示,网关服务启动后,根据以下配置去nacos
拉取不同环境的配置,此处需结合spring.profiles.active
使用,本文不再展开,下文中以prod配置文件演示。
nacos.address=127.0.0.1
nacos.dataId=spring-cloud-gateway-prod.properties
nacos.groupId=DEFAULT_GROUP
nacos.timeout=10
在nacos
相关配置中加入命名空间区分不同环境的配置文件,该命名空间同样需要根据不同环境进行相关的配置。
spring.cloud.nacos.config.namespace=c842a7b3-672d-4e51-81f5-2af3b7573bc7
动态路由配置核心类如下:
@Component
@Slf4j
public class DynamicRouteConfig {
@Autowired
private DynamicRoutePublisher dynamicRoutePublisher;
@Autowired
private NacosGatewayProperties nacosGatewayProperties;
@PostConstruct
public void init(){
// 在服务启动时,其拉取相关配置
dynamicRouteByNacosListener();
}
/**
* 监听Nacos Server下发的动态路由配置
*/
public void dynamicRouteByNacosListener (){
try {
ConfigService configService= NacosFactory.createConfigService(nacosGatewayProperties.getAddress());
String content = configService.getConfig(nacosGatewayProperties.getDa