业务流程
按照我们之前设计的整个网关项目的架构设计
api-gateway-assist
助手工程会被引入到 api-gateway-engine
网关引擎中启动。那么在 api-gateway-assist
启动的过程中,我们希望它所发生的动作,包括启动中的异常、拉取接口信息的失败,以及容器关闭后可以优雅的处理网关通信的关闭,并有日志可以让我们定位。
因此本章节的主要功能内容就是
为各种信息的拉取,一单报错,可以抛出异常并有日志记录进行定位
报错后容器直接关闭的同时,也可以关闭网关通信的channel
所以我们这章节会有如下操作
结合于 api-gateway-assist-03 的工程内容,把网关的注册和拉取配置操作,放到 ApplicationContextAware 接口对应的 setApplicationContext 方法中。这样可以在注册服务以及拉取配置的过程中出现失败情况时,直接抛异常关闭容器。
另外这里还需要做一个容器关闭的监听动作 ApplicationListener<ContextClosedEvent> 容器关闭时则把网关中的通信模块下的 Netty 服务也一起关闭掉。
在之前的章节中我们使用的是ApplicationListener<ContextRefreshedEvent>来进行监听事件,当容器 初始化或刷新完成时 进行向网关中心发起注册,并从网关中心拉取对应的配置。但是这个事件有个缺点,它是只有Spring 启动时(容器完成所有 Bean 的实例化、依赖注入、后置处理等,处于“可用”状态)会触发,这就表明如果随后的注册服务以及拉取配置的过程出现问题,我们是完全不知道的,并且出现问题,容器资源不会释放,因此我们使用ApplicationContextAware,ApplicationListener<ContextClosedEvent> 来进行优化。
为什么这样可以优化呢?
ApplicationListener<ContextRefreshedEvent>是在当所有单例 Bean 创建完成、容器进入“可用状态”之后发布的,这个时候所有的bean已经创建成功,如果在这个点进行注册,拉取操作,有任何问题,对应的bean容器不会因为这个而关闭,处于一种假活状态,这个状态api-gateway-assist似乎可用,但是由于注册,拉取失败,根本无法进行网关通信,如果很多请求打在上面,会极大的浪费资源。
而ApplicationContextAware是出于Bean 创建、依赖注入完成后才会触发的状态,这个状态它仍然属于初始化阶段(initialization)的一部分”,这时 Bean 还没算完全“创建完成”,一旦报错,抛出异常,会被 Spring 当作该 Bean 初始化失败,进而触发 Bean 创建失败 。
ApplicationListener<ContextClosedEvent> ,任何一个bean在在初始化阶段抛异常,容器会认为刷新不成功,于是整个容器就失败,启动过程终止(这里是Bean 的失败反向影响了容器的生命周期),即容器负责创建 Bean;但如果 Bean 没创建好,容器自己也算启动失败。容器失败,我们将立马触发事件关闭通信的channel。
Spring Bean & 容器生命周期关键时间线
┌──────────────────────────── Spring 容器启动 (refresh) ─────────────────────────────┐
│ │
│ 1. 创建 BeanDefinition (扫描/解析配置类) │
│ 2. 实例化 Bean (调用构造器) │
│ 3. 依赖注入 (populate properties) │
│ 4. 初始化阶段 (initialization) │
│ ├─ 调用 Aware 接口回调 │
│ │ • BeanNameAware#setBeanName │
│ │ • BeanFactoryAware#setBeanFactory │
│ │ • ApplicationContextAware#setApplicationContext ← 这里做注册/拉取 │
│ │ │
│ ├─ @PostConstruct / InitializingBean#afterPropertiesSet ← 必须成功的初始化逻辑 │
│ ├─ 调用 BeanPostProcessor#postProcessBefore/AfterInitialization │
│ │
│ 5. 单例 Bean 全部实例化完成 │
│ │
│ 6. 容器刷新完成 → 发布 ContextRefreshedEvent ← 容器 ready,附加初始化/预热任务 │
│ │
└───────────────────────────────────── 应用正常运行 ────────────────────────────────┘
│
│
(可能运行很久)
│
┌───────────────────────────── Spring 容器关闭 (close) ──────────────────────────────┐
│ │
│ 1. 发布 ContextClosedEvent ← 释放资源、反注册、优雅停机 │
│ 2. 调用 DisposableBean#destroy / @PreDestroy / 自定义 destroy-method │
│ 3. BeanPostProcessor#postProcessBeforeDestruction │
│ 4. 销毁单例池 │
│ │
└──────────────────────────────────────── 应用退出 ─────────────────────────────────┘
在这里再补充一下不熟的知识点
注意
本章的内容主要就是对服务的优化处理,完善监听的异常操作处理,让整个流程可以更加顺畅一些。
也是为下一章节服务的整合进行扩展的,这样在后续部署到 Docker 容器中也会更加方便的看到这样的日志,便于调试和处理。
业务实现
本节的业务实现不难,修改的代码只涉及到GatewayApplication.java
,RegisterGatewayService.java
,GatewayAutoConfig.java
这三个类。
首先我们在服务端的RegisterGatewayService.java
中添加对向网关注册中心的注册,拉取请求添加异常的捕捉
package com.zshunbao.gateway.assist.domain.service;
import cn.hutool.http.HttpUtil;
import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.TypeReference;
import com.sun.org.apache.xpath.internal.operations.Bool;
import com.zshunbao.gateway.assist.GatewayException;
import com.zshunbao.gateway.assist.common.Result;
import com.zshunbao.gateway.assist.domain.model.aggregates.ApplicationSystemRichInfo;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import java.util.HashMap;
import java.util.Map;
/**
* @program: api-gateway-assist
* @ClassName RegisterGatewayService
* @description: 网关注册服务
* @author: zs宝
* @create: 2025-08-21 15:17
* @Version 1.0
**/
public class RegisterGatewayService {
private Logger logger = LoggerFactory.getLogger(RegisterGatewayService.class);
/**
* 进行向api-gateway-center网关注册中心发起注册的服务
* @param address 注册中心地址
* @param groupId api-gateway-core分组ID
* @param gatewayId 网关ID
* @param gatewayName 网关名称
* @param gatewayAddress 网关地址
*/
public void doRegister(String address, String groupId, String gatewayId, String gatewayName, String gatewayAddress) {
//封装请求参数
Map<String,Object> paramMap=new HashMap<>();
paramMap.put("groupId", groupId);
paramMap.put("gatewayId", gatewayId);
paramMap.put("gatewayName", gatewayName);
paramMap.put("gatewayAddress", gatewayAddress);
//调用hutool工具包发送请求
String resultStr;
try {
resultStr = HttpUtil.post(address + "/wg/admin/config/registerGateway", paramMap, 550);
} catch (Exception e) {
logger.error("网关服务注册异常,链接资源不可用:{}", address + "/wg/admin/config/registerGateway");
throw e;
}
//将返回结果用自定义的结果类包装
Result<Boolean> result = JSON.parseObject(resultStr,new TypeReference<Result<Boolean>>(){});
logger.info("向网关中心注册网关算力服务 gatewayId:{} gatewayName:{} gatewayAddress:{} 注册结果:{}", gatewayId, gatewayName, gatewayAddress, resultStr);
if(!"0000".equals(result.getCode())){
throw new GatewayException("网关服务注册异常 [gatewayId:" + gatewayId + "] 、[gatewayAddress:" + gatewayAddress + "]");
}
}
public ApplicationSystemRichInfo pullApplicationSystemRichInfo(String address, String gatewayId) {
logger.info("开始向网关注册中心拉取配置 gatewayId:{} ",gatewayId);
//封装请求参数
Map<String,Object> paramMap=new HashMap<>();
paramMap.put("gatewayId",gatewayId);
String resultStr;
try {
resultStr=HttpUtil.post(address+"/wg/admin/config/queryApplicationSystemRichInfo", paramMap, 1200);
} catch (Exception e) {
logger.error("网关服务拉取异常,链接资源不可用:{}", address + "/wg/admin/config/queryApplicationSystemRichInfo");
throw e;
}
Result<ApplicationSystemRichInfo> result = JSON.parseObject(resultStr, new TypeReference<Result<ApplicationSystemRichInfo>>(){});
if (!"0000".equals(result.getCode()))
throw new GatewayException("从网关中心拉取应用服务和接口的配置信息到本地完成注册异常 [gatewayId:" + gatewayId + "]");
logger.info("从网关注册中心拉取配置成功 gatewayId:{} 配置信息 {}",gatewayId,resultStr);
return result.getData();
}
}
其次由于我们本次在涉及到网关通信channel的关闭,因此我们的配置有关channel处,要将api-gateway-core中的channel专门命名做一个区分。GatewayAutoConfig.java
package com.zshunbao.gateway.assist.config;
import com.zshunbao.gateway.assist.application.GatewayApplication;
import com.zshunbao.gateway.assist.domain.service.RegisterGatewayService;
import com.zshunbao.gateway.core.session.defaults.DefaultGatewaySessionFactory;
import com.zshunbao.gateway.core.socket.GatewaySocketServer;
import io.netty.channel.Channel;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.boot.context.properties.EnableConfigurationProperties;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import java.util.concurrent.ExecutionException;
import java.util.concurrent.Executors;
import java.util.concurrent.Future;
/**
* @program: api-gateway-assist
* @ClassName GatewayAutoConfig
* @description: 网关配置服务,这里利用了Java的 SPI机制进行bean创建
* @author: zs宝
* @create: 2025-08-21 15:30
* @Version 1.0
**/
@Configuration
@EnableConfigurationProperties(GatewayServiceProperties.class)
public class GatewayAutoConfig {
private Logger logger = LoggerFactory.getLogger(GatewayAutoConfig.class);
@Bean
public RegisterGatewayService registerGatewayService(){
return new RegisterGatewayService();
}
@Bean
public GatewayApplication gatewayApplication(GatewayServiceProperties properties,RegisterGatewayService registerGatewayService, com.zshunbao.gateway.core.session.Configuration configuration,Channel gatewaySocketServerChannel){
return new GatewayApplication(properties,registerGatewayService,configuration,gatewaySocketServerChannel);
}
/**
* 创建网关配置对象 Configuration 用于贯穿整个网关核心通信
* @return
*/
@Bean
public com.zshunbao.gateway.core.session.Configuration gatewayCoreConfiguration(GatewayServiceProperties properties){
com.zshunbao.gateway.core.session.Configuration configuration=new com.zshunbao.gateway.core.session.Configuration();
//配置好相关的网管地址和端口号
String[] split = properties.getGatewayAddress().split(":");
configuration.setHostName(split[0].trim());
configuration.setPort(Integer.parseInt(split[1].trim()));
return configuration;
}
/**
* 初始化网关服务,创建服务端channel对象,方便获取和控制网关操作
* @param configuration
* @return
*/
@Bean("gatewaySocketServerChannel")
public Channel initGateway(com.zshunbao.gateway.core.session.Configuration configuration) throws ExecutionException, InterruptedException {
//1、基于配置构建网络会话工厂
DefaultGatewaySessionFactory gatewaySessionFactory=new DefaultGatewaySessionFactory(configuration);
//2、创建启动网关核心通信的服务
GatewaySocketServer server=new GatewaySocketServer(configuration,gatewaySessionFactory);
Future<Channel> future= Executors.newFixedThreadPool(2).submit(server);
Channel channel = future.get();
if (null == channel) throw new RuntimeException("api gateway core netty server start error channel is null");
while (!channel.isActive()){
logger.info("api gateway core netty server gateway start Ing ...");
Thread.sleep(500);
}
logger.info("api gateway core netty server gateway start Done! {}", channel.localAddress());
return channel;
}
}
最后也是本章节的重点,在bean创建,依赖注入完成后,但是bean却又没有完全初始化创建成功时,触发向网关注册中心发起注册,并拉取配置的信息,同时抓取相关异常。并在最后监听容器关闭事件,关闭后关闭网关通信。
在 setApplicationContext 方法中步骤1和步骤2的代码相对于前面章节并没有改变,只是这部分代码从以前的监听类中放到了这里来管理,方便异常时直接关闭容器。
监听到 Spring 的容器关闭通知时,则把 Netty 服务关闭掉。
测试
本章的测试重点在于服务的启动链接注册中心异常时的容器关闭动作,以及应用程序退出时,对网关中的 Netty 服务进行关闭。
启动zookeeper,api-gateway-test-provider,api-gateway-center 注册中心
修改 api-gateway-assist-00 pom 引入 api-gateway-assist-04
更新网关注册中心的数据库
SET NAMES utf8mb4;
SET FOREIGN_KEY_CHECKS = 0;
-- ----------------------------
-- Table structure for application_interface
-- ----------------------------
DROP TABLE IF EXISTS `application_interface`;
CREATE TABLE `application_interface` (
`id` int(11) NOT NULL AUTO_INCREMENT COMMENT '自增主键',
`system_id` varchar(64) COLLATE utf8_bin DEFAULT NULL COMMENT '系统标识',
`interface_id` varchar(64) COLLATE utf8_bin DEFAULT NULL COMMENT '接口标识',
`interface_name` varchar(128) COLLATE utf8_bin DEFAULT NULL COMMENT '接口名称',
`interface_version` varchar(16) COLLATE utf8_bin DEFAULT NULL COMMENT '接口版本',
`create_time` datetime DEFAULT NULL COMMENT '创建时间',
`update_time` datetime DEFAULT NULL COMMENT '更新时间',
PRIMARY KEY (`id`),
UNIQUE KEY `idx` (`system_id`,`interface_id`) USING BTREE
) ENGINE=InnoDB AUTO_INCREMENT=2 DEFAULT CHARSET=utf8 COLLATE=utf8_bin;
-- ----------------------------
-- Records of application_interface
-- ----------------------------
BEGIN;
INSERT INTO `application_interface` VALUES (1, 'api-gateway-test', 'cn.bugstack.gateway.rpc.IActivityBooth', '活动接口', '1.0.0', '2022-11-13 13:13:00', '2022-11-13 13:13:00');
COMMIT;
-- ----------------------------
-- Table structure for application_interface_method
-- ----------------------------
DROP TABLE IF EXISTS `application_interface_method`;
CREATE TABLE `application_interface_method` (
`id` int(11) NOT NULL AUTO_INCREMENT COMMENT '自增主键',
`system_id` varchar(64) COLLATE utf8_bin DEFAULT NULL COMMENT '系统标识',
`interface_id` varchar(64) COLLATE utf8_bin DEFAULT NULL COMMENT '接口标识',
`method_id` varchar(64) COLLATE utf8_bin DEFAULT NULL COMMENT '方法标识',
`method_name` varchar(128) COLLATE utf8_bin DEFAULT NULL COMMENT '方法名称',
`parameter_type` varchar(256) COLLATE utf8_bin DEFAULT NULL COMMENT '参数类型;(RPC 限定单参数注册);new String[]{"java.lang.String"}、new String[]{"cn.bugstack.gateway.rpc.dto.XReq"}',
`uri` varchar(126) COLLATE utf8_bin DEFAULT NULL COMMENT '网关接口',
`http_command_type` varchar(32) COLLATE utf8_bin DEFAULT NULL COMMENT '接口类型;GET、POST、PUT、DELETE',
`auth` int(4) DEFAULT NULL COMMENT 'true = 1是、false = 0否',
`create_time` datetime DEFAULT NULL COMMENT '创建时间',
`update_time` datetime DEFAULT NULL COMMENT '更新时间',
PRIMARY KEY (`id`),
UNIQUE KEY `idx` (`system_id`,`interface_id`,`method_id`) USING BTREE
) ENGINE=InnoDB AUTO_INCREMENT=3 DEFAULT CHARSET=utf8 COLLATE=utf8_bin;
-- ----------------------------
-- Records of application_interface_method
-- ----------------------------
BEGIN;
INSERT INTO `application_interface_method` VALUES (1, 'api-gateway-test', 'cn.bugstack.gateway.rpc.IActivityBooth', 'sayHi', '测试方法', 'java.lang.String', '/wg/activity/sayHi', 'GET', 0, '2022-11-13 13:16:52', '2022-11-13 13:16:52');
INSERT INTO `application_interface_method` VALUES (2, 'api-gateway-test', 'cn.bugstack.gateway.rpc.IActivityBooth', 'insert', '插入方法', 'cn.bugstack.gateway.rpc.dto.XReq', '/wg/activity/insert', 'POST', 1, '2022-11-13 13:16:52', '2022-11-13 13:16:52');
COMMIT;
-- ----------------------------
-- Table structure for application_system
-- ----------------------------
DROP TABLE IF EXISTS `application_system`;
CREATE TABLE `application_system` (
`id` int(11) NOT NULL AUTO_INCREMENT COMMENT '自增主键',
`system_id` varchar(64) COLLATE utf8_bin DEFAULT NULL COMMENT '系统标识',
`system_name` varchar(128) COLLATE utf8_bin DEFAULT NULL COMMENT '系统名称',
`system_type` varchar(4) COLLATE utf8_bin DEFAULT NULL COMMENT '系统类型;RPC、HTTP',
`system_registry` varchar(128) COLLATE utf8_bin DEFAULT NULL COMMENT '注册中心',
`create_time` datetime DEFAULT NULL COMMENT '创建时间',
`update_time` datetime DEFAULT NULL COMMENT '更新时间',
PRIMARY KEY (`id`),
UNIQUE KEY `idx_systemId` (`system_id`) USING BTREE
) ENGINE=InnoDB AUTO_INCREMENT=4 DEFAULT CHARSET=utf8 COLLATE=utf8_bin;
-- ----------------------------
-- Records of application_system
-- ----------------------------
BEGIN;
INSERT INTO `application_system` VALUES (1, 'lottery-api', '抽奖API系统', 'RPC', 'zookeeper://127.0.0.1:2181', '2022-11-13 13:10:03', '2022-11-13 13:10:03');
INSERT INTO `application_system` VALUES (3, 'api-gateway-test', '网关测试系统', 'RPC', 'zookeeper://127.0.0.1:2181', '2022-11-13 13:12:54', '2022-11-13 13:12:54');
COMMIT;
-- ----------------------------
-- Table structure for gateway_distribution
-- ----------------------------
DROP TABLE IF EXISTS `gateway_distribution`;
CREATE TABLE `gateway_distribution` (
`id` int(11) NOT NULL COMMENT '自增主键',
`group_id` varchar(64) COLLATE utf8_bin DEFAULT NULL COMMENT '分组标识',
`gateway_id` varchar(64) COLLATE utf8_bin DEFAULT NULL COMMENT '网关标识',
`system_id` varchar(64) COLLATE utf8_bin DEFAULT NULL COMMENT '系统标识',
`system_name` varchar(128) COLLATE utf8_bin DEFAULT NULL COMMENT '系统名称',
`create_time` datetime DEFAULT NULL COMMENT '创建时间',
`update_time` datetime DEFAULT NULL COMMENT '更新时间',
PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE=utf8_bin;
-- ----------------------------
-- Records of gateway_distribution
-- ----------------------------
BEGIN;
INSERT INTO `gateway_distribution` VALUES (1, '10001', 'api-gateway-g4', 'api-gateway-test', '测试工程', '2022-11-26 13:13:00', '2022-11-26 13:13:00');
COMMIT;
-- ----------------------------
-- Table structure for gateway_server
-- ----------------------------
DROP TABLE IF EXISTS `gateway_server`;
CREATE TABLE `gateway_server` (
`id` int(11) NOT NULL AUTO_INCREMENT COMMENT '自增主键',
`group_id` varchar(64) COLLATE utf8_bin DEFAULT NULL COMMENT '分组标识',
`group_name` varchar(128) COLLATE utf8_bin DEFAULT NULL COMMENT '分组名称',
PRIMARY KEY (`id`)
) ENGINE=InnoDB AUTO_INCREMENT=2 DEFAULT CHARSET=utf8 COLLATE=utf8_bin;
-- ----------------------------
-- Records of gateway_server
-- ----------------------------
BEGIN;
INSERT INTO `gateway_server` VALUES (1, '10001', '缺省的');
COMMIT;
-- ----------------------------
-- Table structure for gateway_server_detail
-- ----------------------------
DROP TABLE IF EXISTS `gateway_server_detail`;
CREATE TABLE `gateway_server_detail` (
`id` int(11) NOT NULL AUTO_INCREMENT COMMENT '自增主键',
`group_id` varchar(32) COLLATE utf8_bin DEFAULT NULL COMMENT '分组标识',
`gateway_id` varchar(32) COLLATE utf8_bin DEFAULT NULL COMMENT '网关标识',
`gateway_name` varchar(128) COLLATE utf8_bin DEFAULT NULL COMMENT '网关名称',
`gateway_address` varchar(64) COLLATE utf8_bin DEFAULT NULL COMMENT '网关地址:127.0.0.1',
`status` varchar(4) COLLATE utf8_bin DEFAULT NULL COMMENT '服务状态:0不可用、1可使用',
`create_time` datetime DEFAULT NULL ON UPDATE CURRENT_TIMESTAMP COMMENT '创建时间',
`update_time` datetime DEFAULT NULL ON UPDATE CURRENT_TIMESTAMP COMMENT '更新时间',
PRIMARY KEY (`id`),
UNIQUE KEY `idx_gateway` (`gateway_id`,`gateway_address`) USING BTREE
) ENGINE=InnoDB AUTO_INCREMENT=17 DEFAULT CHARSET=utf8 COLLATE=utf8_bin;
-- ----------------------------
-- Records of gateway_server_detail
-- ----------------------------
BEGIN;
INSERT INTO `gateway_server_detail` VALUES (13, '10001', 'api-gateway-g1', '电商支付网关', '127.0.0.196', '1', '2022-11-06 15:22:11', '2022-11-06 15:22:11');
INSERT INTO `gateway_server_detail` VALUES (14, '10001', 'api-gateway-g2', '电商支付网关', '127.0.0.197', '1', '2022-11-06 15:22:11', '2022-11-06 15:22:11');
INSERT INTO `gateway_server_detail` VALUES (15, '10001', 'api-gateway-g3', '电商配送网关', '127.0.0.198', '1', '2022-11-06 15:23:19', '2022-11-06 15:23:19');
INSERT INTO `gateway_server_detail` VALUES (16, '10001', 'api-gateway-g4', '电商配送网关', '127.0.0.1:7397', '1', '2022-12-03 15:36:19', '2022-12-03 15:36:19');
COMMIT;
-- ----------------------------
-- Table structure for http_statement
-- ----------------------------
DROP TABLE IF EXISTS `http_statement`;
CREATE TABLE `http_statement` (
`id` bigint(11) NOT NULL AUTO_INCREMENT,
`application` varchar(128) COLLATE utf8_bin NOT NULL COMMENT '应用名称',
`interface_name` varchar(256) COLLATE utf8_bin NOT NULL COMMENT '服务接口;RPC、其他',
`method_name` varchar(128) COLLATE utf8_bin NOT NULL COMMENT ' 服务方法;RPC#method',
`parameter_type` varchar(256) COLLATE utf8_bin NOT NULL COMMENT '参数类型(RPC 限定单参数注册);new String[]{"java.lang.String"}、new String[]{"cn.bugstack.gateway.rpc.dto.XReq"}',
`uri` varchar(128) COLLATE utf8_bin NOT NULL COMMENT '网关接口',
`http_command_type` varchar(32) COLLATE utf8_bin NOT NULL COMMENT '接口类型;GET、POST、PUT、DELETE',
`auth` int(4) NOT NULL DEFAULT '0' COMMENT 'true = 1是、false = 0否',
`create_time` datetime DEFAULT NULL ON UPDATE CURRENT_TIMESTAMP COMMENT '创建时间',
`update_time` datetime DEFAULT NULL ON UPDATE CURRENT_TIMESTAMP COMMENT '更新时间',
PRIMARY KEY (`id`)
) ENGINE=InnoDB AUTO_INCREMENT=3 DEFAULT CHARSET=utf8 COLLATE=utf8_bin;
-- ----------------------------
-- Records of http_statement
-- ----------------------------
BEGIN;
INSERT INTO `http_statement` VALUES (1, 'api-gateway-test', 'cn.bugstack.gateway.rpc.IActivityBooth', 'sayHi', 'java.lang.String', '/wg/activity/sayHi', 'GET', 0, '2022-10-22 15:30:00', '2022-10-22 15:30:00');
INSERT INTO `http_statement` VALUES (2, 'api-gateway-test', 'cn.bugstack.gateway.rpc.IActivityBooth', 'insert', 'cn.bugstack.gateway.rpc.dto.XReq', '/wg/activity/insert', 'POST', 1, '2022-10-22 15:30:00', '2022-10-22 15:30:00');
COMMIT;
SET FOREIGN_KEY_CHECKS = 1;
启动:api-gateway-assist-00 确保 pom 引入的是最新的 api-gateway-assist-04