Nacos 接入示例
本示例演示如何在 VextJS 中集成 Nacos,实现服务注册与发现、运行期动态配置,以及启动期远程配置补丁。
VextJS 提供官方 Nacos 插件 vextjs-nacos,封装了注册/发现与运行期配置订阅流程。对于必须在框架配置冻结前生效的内容(如数据库配置),应使用 src/config/bootstrap.ts 的 bootstrap config provider。
推荐分层使用:
- 服务注册/发现、运行期动态开关:直接使用官方插件
vextjs-nacos - 启动期数据库/密钥/基础设施配置:使用
src/config/bootstrap.ts拉取 Nacos 配置并返回 patch :::
前置条件
- Nacos Server 2.x(已实测 nacos@2.6.1)
- Node.js >= 18
- VextJS >= 0.3.2
一、推荐:使用 vextjs-nacos 官方插件
1. 安装
2. 配置(src/config/default.ts)
说明:
config适合单配置场景configs适合基础配置 + 环境覆盖配置拆分- 当两者同时存在时,会按
config -> configs[0] -> configs[1] ...顺序合并,后者优先
3. 注册插件(src/plugins/nacos.ts)
也支持显式传参(覆盖 app.config.nacos):
动态端口(推荐:与 app.config.port 保持一致)
config/default.ts 中的 service.port 是静态值,无法读取最终合并后的端口号。
若各环境端口不同(如 sit: 10019 / prod: 20019),推荐在插件中动态注入:
这样 config/default.ts 里 service.port 仅作类型占位,实际注册端口由 app.config.port 决定,
各环境只需在对应 config 文件设置 port: 10019,nacos 自动跟随。
3.1 启动期远程配置推荐走 src/config/bootstrap.ts
如果你希望在 MonSQLize 初始化之前 就从 Nacos 拉取数据库配置,不要把这一步放在普通插件里;推荐直接使用 vextjs-nacos 提供的 createNacosBootstrapProvider():
这样配置优先级会进入正式链路:default < env < local < provider < CLI。
:::info 当前边界
createNacosBootstrapProvider() 只负责启动期批量拉取并深合并 JSON 对象 patch,适合数据库、密钥、基础设施配置这类“必须在配置冻结前生效”的内容。
这份返回值会进入 app.config 的 provider patch 合并链路,不会自动变成 app.remoteConfig。
它不负责:
- 服务注册
- 服务发现
app.nacos挂载app.remoteConfig注入与运行期订阅更新
这些运行期能力仍然由 nacosPlugin() 负责。
如果你需要:
- 服务注册 / 服务发现
- 与插件一致的
app.remoteConfig行为 - 配置变更后的持续订阅更新
都应该继续在 src/plugins/nacos.ts 中使用 nacosPlugin() 处理,而不是在 bootstrap 阶段完成。
3.1.1 bootstrap.ts 里能不能做服务发现?
默认不能直接使用 app.nacos!.discover()。
原因是 src/config/bootstrap.ts 运行在 Vext App 创建之前:
- 此时还没有
app nacosPlugin()也还没有执行- 因而不存在
app.nacos/app.remoteConfig
所以推荐边界是:
- 启动期只做配置 patch 拉取 →
createNacosBootstrapProvider() - 运行期服务注册 / 服务发现 / 配置订阅 →
nacosPlugin()
3.2 运行期动态配置继续使用 app.remoteConfig
如果配置只影响运行期功能开关、灰度策略、外部 API 地址等,不需要参与 database / plugins / middlewares 初始化,则直接使用 vextjs-nacos 的配置订阅能力即可:
- 初次启动后插件会拉取 Nacos 配置并挂载到
app.remoteConfig - 后续配置变更会自动更新
app.remoteConfig - 无需重启服务
完成。插件自动完成:
- ✅ 启动时注册当前服务实例到 Nacos
- ✅ 拉取并订阅配置中心,自动更新
app.remoteConfig - ✅ 关闭时按 LIFO 顺序:先
deregisterInstance(停流量)→ 再configClient.close() - ✅ TypeScript 类型自动增强
app.nacos/app.remoteConfig/config.nacos
4. 使用服务发现
如需高级负载均衡策略(权重 / 一致性哈希),可直接使用 app.nacos!.naming.selectInstances(...) 调用 nacos SDK 原生 API。
5. 使用远程配置
Nacos 配置内容须为合法 JSON。配置变更时,
app.remoteConfig会自动更新(无需重启服务)。在路由 handler 中若要读取这类运行期可能被
app.extend()替换引用的字段,建议优先使用req.app.remoteConfig,而不是闭包app.remoteConfig。原因是defineRoutes()传入的闭包app来自 collector 拷贝;当插件后续用app.extend("remoteConfig", nextValue)替换为新对象时,闭包里捕获的旧引用不会自动刷新。
多配置运行期示例
这种方式适合:
- 基础开关 + 环境覆盖
- 通用服务配置 + 租户/区域增量配置
- 运行期灰度参数分层维护
二、最佳实践
服务发现缓存(高频调用场景)
discover() 每次都查询 Nacos。高 QPS 场景建议加本地缓存:
Nacos SDK 的
subscribe内部已维护实例列表的本地缓存,所以即使不加上层缓存也已较高效。本地缓存的主要意义是避免每次 discover 调用 selectInstances 的开销。
健康检查端点
Nacos 配置数据格式
控制台中创建配置时使用 JSON:
修改后 vext 应用会通过订阅自动接收变更,无需重启。
三、下一步
- 📦
vextjs-nacosnpm 包 — 完整 API 文档与变更日志 - 🔭 OpenTelemetry 接入示例 — 完整可观测性
- 🔌 插件系统 —
definePlugin()自定义插件 - 🌐 app.fetch — 内置 HTTP 客户端(超时/重试/requestId 传播)