ElIauk

Nacos 注册中心入门与踩坑

注册中心到底解决了什么问题 单体应用里,A 调 B 就是一次方法调用;拆成微服务后,A 需要知道 B 的地址,而 B 的地址会随扩缩容、发版、故障漂移不断变化。注册中心负责三件事:服务启动时登记自己,调用方按服务名拉取可用实例,实例下线或心跳超时后被摘除。Nacos 把这套能力和配置中心放在同一个进

评论
Nacos 注册中心入门与踩坑

注册中心到底解决了什么问题

单体应用里,A 调 B 就是一次方法调用;拆成微服务后,A 需要知道 B 的地址,而 B 的地址会随扩缩容、发版、故障漂移不断变化。注册中心负责三件事:服务启动时登记自己,调用方按服务名拉取可用实例,实例下线或心跳超时后被摘除。Nacos 把这套能力和配置中心放在同一个进程里,所以 2025 年的 Spring Cloud Alibaba 项目仍然大量用它。

但“注册上了”和“能调通”是两件事。很多人第一次接 Nacos,控制台里服务列表明明是绿的,Feign 调用却报 No instances available for order-service,或者请求打到一个已经停掉的 Pod 上。下面按接入顺序讲清楚,再集中说坑。

版本和端口先对齐

组件 本文示例 说明
JDK 21 LTS,Spring Boot 3.x 的基线
Spring Boot 3.3.x 3.4 也可,但 Cloud 版本要配套
Spring Cloud 2023.0.x 与 Boot 3.3 对应
Spring Cloud Alibaba 2023.0.3.x 引入 Nacos 客户端
Nacos Server 2.4.x 服务端独立部署

需要特别记住:Nacos 2.x 不是只开 8848。客户端通过 gRPC 长连接通信,还需要 9848(客户端请求服务端)和 9849(服务端间同步)。只映射 8848 时,控制台能打开、服务也可能注册成功,但心跳和推送会超时,表现为实例反复上下线。容器部署时三个端口都要暴露,或者干脆用 host 网络。

最小可用配置

引入依赖后,spring.application.name 就是服务名,不需要再写 @EnableDiscoveryClient:

<dependency>
    <groupId>com.alibaba.cloud</groupId>
    <artifactId>spring-cloud-starter-alibaba-nacos-discovery</artifactId>
</dependency>
server:
  port: 8081
spring:
  application:
    name: order-service
  cloud:
    nacos:
      discovery:
        server-addr: 127.0.0.1:8848
        namespace: dev-id
        group: ORDER_GROUP
        username: nacos
        password: ${NACOS_PASSWORD}

namespace 要填命名空间的 ID,不是显示名称;group 要和消费方一致,默认都是 DEFAULT_GROUP。这两项只要有一项对不上,控制台看到的就是两个互不相干的服务。密码不要硬编码,走环境变量或密钥管理。

临时实例、心跳与保护阈值

默认注册的是临时实例(ephemeral: true):客户端每 5 秒发一次心跳,15 秒没心跳标记不健康,30 秒后摘除。这套机制适合无状态的 Spring Boot 应用。如果服务是数据库、旧系统这类“进程在但心跳机制不适用”的场景,可以注册为持久实例,由服务端主动探测。

还有一个容易被忽略的开关是保护阈值。当健康实例占比低于阈值时,Nacos 会把全部实例(包括不健康的)返回给调用方,避免流量瞬间归零。这个设计本意是保可用性,但调用方如果没配重试,就可能把请求打到坏实例上。所以保护阈值要结合客户端的重试和超时一起看,不能只调注册中心。

常见坑与排查顺序

坑一:namespace 填了名字。 控制台显示 dev,配置里写 namespace: dev,实际 ID 是一串 UUID,结果服务注册到了 public。以控制台命名空间详情里的 ID 为准。

坑二:Docker 里注册了容器 IP。 容器使用 bridge 网络时,Nacos 客户端默认取容器网卡地址,宿主机和其他机器根本路由不到。可以显式指定 spring.cloud.nacos.discovery.ip,或选择正确的 network-interface,生产上更推荐让 Pod 使用可路由的 CNI 地址。

坑三:服务名带下划线或大小写混用。 Nacos 对服务名敏感,order_service 和 order-service 是两个服务。团队内最好用 Maven 的 artifactId 统一生成,不要手写。

坑四:只改了一半环境。 注册中心和配置中心的 namespace、group、账号密码是分开配置的,改了一个忘了另一个,启动时配置拉不到,服务却还能注册。

真出问题时按这个顺序查:先看 Nacos 控制台的服务列表和实例数,确认注册成功;再调 /nacos/v1/ns/instance/list?serviceName=order-service 看接口返回;然后看客户端 logs/nacos/naming.log 有没有心跳失败或连接超时;最后在调用方打日志确认拿到的实例列表。多数“找不到服务”的问题,最后都落在 namespace/group 不一致、9848 端口不通、或者客户端缓存了旧列表这三类上。

参考

评论

推荐阅读

订阅邮件

订阅更新,及时收到最新文章。

作者