API 网关(yidun-api-gateway)
全站唯一外部入口。基于 Apache ShenYu 2.5.0 二次开发,插件链在转发前完成签名、令牌与功能权限校验。
1. 业务定位
把分散在各后端服务里的 HTTP / Dubbo 接口收敛成一个接入面,保证只有「认证通过且拥有对应功能权限」的调用方能触达内网服务。
三个 Maven 子工程:
| 子工程 | 角色 |
|---|---|
shenyu-admin | 管理面:插件/选择器/规则/元数据/字典/账号权限配置,持久化 MySQL |
shenyu-bootstrap | 数据面:Spring Boot WebFlux + Netty 运行时网关,端口 9195 |
yidun-shenyu-client | 接入 SDK:后端服务用注解注册接口元数据 |
2. 核心链路
配置流与流量流是两条独立的路径:
3. 关键组件
| 组件 | 职责 |
|---|---|
YidunAuthPlugin | 平台签名校验、功能权限判定 |
PlatformSignService | 签名算法实现 |
JwtExtPlugin | 用户令牌解析与校验 |
FunctionPermissionCache | URL → 功能权限映射缓存(来自权限中心) |
HealthFilter / HealthCheckAPI | 健康检查与上下线 |
ShenyuSpringMvcClient / ShenyuDubboClient | 后端注册注解,带 yidunPermission 元数据 |
ShenyuClientHttpRegistryController | 隔离环境注册 |
4. 鉴权顺序
顺序不可调整:签名证明「是谁的客户端」,令牌证明「是哪个用户」,权限证明「这个用户能不能调这个接口」。
5. 上下游依赖
| 方向 | 模块 | 说明 |
|---|---|---|
| 下游 | union-admin | FunctionPermissionCache、令牌注销服务 |
| 下游 | mplatform-event | @EnableEventClient 事件上报,刷新权限缓存 |
| 上游 | 所有后端服务 | 通过 yidun-shenyu-client 注册接口元数据 |
6. 工程约束与变更红线
- 鉴权禁止下放:网关是唯一鉴权点,后端服务不应重复实现同等校验。
- 插件顺序是安全边界:签名 → 令牌 → 权限,调换会造成越权。
- 权限缓存必须有兜底刷新:事件漏发时靠对账任务补齐。
- 接口注册元数据要与权限项一致:
yidunPermission配错会导致「有权限也调不通」或「无权限也能调」。 - 多环境隔离:
shenyu-admin支持隔离环境注册,禁止跨环境注册。
7. 关键代码索引
| 主题 | 路径 | 说明 |
|---|---|---|
| 鉴权插件 | yidun-api-gateway/shenyu-bootstrap/src/main/java/.../plugin/YidunAuthPlugin.java | 签名与权限 |
| 签名服务 | yidun-api-gateway/shenyu-bootstrap/src/main/java/.../service/PlatformSignService.java | 签名算法 |
| JWT 插件 | yidun-api-gateway/shenyu-bootstrap/src/main/java/.../plugin/JwtExtPlugin.java | 令牌校验 |
| 健康检查 | yidun-api-gateway/shenyu-bootstrap/src/main/java/.../filter/HealthFilter.java | 上下线 |
| 客户端注解 | yidun-api-gateway/yidun-shenyu-client/src/main/java/.../ShenyuSpringMvcClient.java | 接口注册 |
| 配置分发 | yidun-api-gateway/shenyu-admin/src/main/java/.../disruptor/DataChangedEventDispatcher.java | 配置变更 |
| WebSocket 推送 | yidun-api-gateway/shenyu-admin/src/main/java/.../WebsocketCollector.java | 下发到 bootstrap |
8. 排查要点
| 现象 | 定位 | 结论 |
|---|---|---|
| 请求 404/503 | 看 selector/rule 是否匹配到后端 | 服务未注册或元数据缺失 |
| 签名校验失败 | 看签名原文、时间戳、密钥 | 客户端算法或时钟问题 |
| 令牌失效 | 看令牌签发与注销记录 | 用户登出或被踢下 |
| 有权限仍 403 | 看 FunctionPermissionCache 是否最新 | 权限事件未下发 |
| 新接口调不通 | 看是否用注解注册成功 | 未注册 = 网关不认识该路由 |
| 网关整体变慢 | 看插件耗时与缓存命中 | 权限缓存回源是常见原因 |