9.4.1 服务注册与发现概述与工作流程
本节介绍服务注册与发现的核心概念、角色分工与端到端流程,帮助理解 Nacos 在微服务体系中的定位。服务注册是服务提供方将实例信息上报到注册中心;服务发现是服务消费方从注册中心获取可用实例并建立调用关系。两者共同构成服务治理的基础能力,确保服务的可用性、伸缩性与动态变更的可控性。
核心角色与概念#
- 服务提供者(Provider):对外暴露接口的应用实例,负责注册自身信息并维持健康心跳。
- 服务消费者(Consumer):调用服务的应用实例,通过发现机制获取可用服务列表。
- 注册中心(Nacos):保存服务元数据与实例状态,提供查询、订阅、推送、健康检查等能力。
- 服务实例:服务的具体运行实体,包含 IP、端口、协议、权重、健康状态等属性。
- 元数据:服务特性描述,如版本、机房、环境标签,用于路由与治理。
服务注册与发现原理草图#
服务注册与发现工作流程#
-
服务启动与注册
服务提供者启动后向 Nacos 发送注册请求,包含服务名、实例地址、端口、权重、元数据等信息。Nacos 写入内存并持久化,形成服务实例列表。 -
健康检查与心跳维持
服务提供者按周期发送心跳或由 Nacos 进行健康探测,维持实例状态。心跳超时或探测失败会将实例标记为不健康或剔除。 -
服务订阅与发现
服务消费者启动后向 Nacos 发起服务订阅或查询请求,获取可用实例列表。可根据命名空间、分组、集群等范围进行过滤。 -
变更推送与列表更新
当实例上下线或状态变更时,Nacos 通过长轮询/推送机制通知消费者,更新本地实例缓存,保持调用链路实时一致。 -
客户端负载均衡调用
消费者根据本地实例列表进行负载均衡选择,如权重、就近优先或自定义路由策略,完成服务调用。
快速安装与验证(本机单机示例)#
# 1) 启动 Nacos 单机(Docker)
docker run -d --name nacos-standalone \
-e MODE=standalone \
-p 8848:8848 \
nacos/nacos-server:v2.3.1
# 2) 检查端口与健康
curl -s http://127.0.0.1:8848/nacos/actuator/health | jq
# 预期: {"status":"UP", ...}
# 3) 登录 Web 控制台(默认账号/密码)
# http://127.0.0.1:8848/nacos nacos/nacos
命令说明:
- MODE=standalone 以单机模式启动。
- 8848 为默认控制台与 API 端口。
- actuator/health 用于快速确认服务状态。
注册与发现 OpenAPI 示例(可执行)#
# 环境变量
export NACOS_ADDR="127.0.0.1:8848"
export NS="public"
export GROUP="DEFAULT_GROUP"
export SERVICE="order-service"
# 1) 注册实例
curl -X POST "http://$NACOS_ADDR/nacos/v1/ns/instance" \
-d "serviceName=$SERVICE" \
-d "ip=192.168.10.11" \
-d "port=8081" \
-d "weight=1.0" \
-d "namespaceId=$NS" \
-d "groupName=$GROUP" \
-d "metadata[version]=v1"
# 2) 发送心跳
curl -X PUT "http://$NACOS_ADDR/nacos/v1/ns/instance/beat" \
-d "serviceName=$SERVICE" \
-d "ip=192.168.10.11" \
-d "port=8081" \
-d "namespaceId=$NS" \
-d "groupName=$GROUP"
# 3) 服务发现(查询实例列表)
curl -s "http://$NACOS_ADDR/nacos/v1/ns/instance/list?serviceName=$SERVICE&namespaceId=$NS&groupName=$GROUP" | jq
# 4) 注销实例
curl -X DELETE "http://$NACOS_ADDR/nacos/v1/ns/instance" \
-d "serviceName=$SERVICE" \
-d "ip=192.168.10.11" \
-d "port=8081" \
-d "namespaceId=$NS" \
-d "groupName=$GROUP"
预期效果:
- instance/list 返回 hosts 数组,包含 IP、端口、健康状态等字段。
- 注册后在控制台「服务列表」可见 order-service。
关键流程要点#
- 注册中心高可用:确保注册与发现持续可用,避免单点故障。
- 实例列表本地缓存:降低注册中心压力,提升调用稳定性。
- 一致性与实时性权衡:通过增量推送与缓存策略平衡性能与同步速度。
- 服务治理扩展:基于注册与发现结果可叠加路由、限流、熔断与灰度发布等策略。
常见排错与定位#
# 1) 无法注册:检查 Nacos 端口与 API 可用性
ss -lntp | grep 8848
curl -s http://127.0.0.1:8848/nacos/actuator/health | jq
# 2) 服务不健康:检查心跳是否持续发送
# 查看 Nacos 日志(容器)
docker logs --tail=200 nacos-standalone | grep -i "beat"
# 3) 服务列表为空:核对命名空间/分组/服务名
# 查询服务列表(默认 public + DEFAULT_GROUP)
curl -s "http://127.0.0.1:8848/nacos/v1/ns/service/list?pageNo=1&pageSize=10&namespaceId=public&groupName=DEFAULT_GROUP" | jq
# 4) 实例已注册但不可发现:检查是否被标记不健康
curl -s "http://127.0.0.1:8848/nacos/v1/ns/instance/list?serviceName=order-service" | jq '.hosts[] | {ip,port,healthy}'
排错要点:
- 80% 的问题来自 命名空间/分组/服务名不一致。
- 心跳间隔过长会导致实例被剔除。
- 控制台与 API 查询的过滤条件务必一致。
练习#
- 使用 OpenAPI 注册两个实例(不同 IP/端口),观察
instance/list返回的hosts数量与权重。 - 停止一个实例心跳 2 分钟,验证 Nacos 将其标记为不健康的时间点。
- 将同一服务注册到不同
groupName,对比不同分组下的发现结果。