Spring Cloud:分布式系统的“粘合剂”(六)
2026/8/24 13:34:43 网站建设 项目流程

专栏:Spring Cloud

个人主页:手握风云

目录

一、Nacos 健康检查机制

二、Nacos 环境隔离

三、Nacos 配置中心

3.1. 解决痛点

3.2. 快速上手

四、Nacos VS Eureka

4.1. 相同点

4.2. 核心差异


一、Nacos 健康检查机制

作为注册中心,Nacos 需要实时感知各个服务实例的运行健康状态,这样才能够给服务调用方提供可靠可用的实例信息。Nacos 一共提供了两套完全不同的健康检查实现机制,分别是客户端主动上报机制与服务端反向探测机制。

客户端主动上报,指由服务实例客户端定期向 Nacos 服务端发送心跳,以此上报自身存活状态。这套机制默认心跳上报间隔为 5 秒。当 Nacos 超过 15 秒没有收到某个实例的心跳,就会把该实例标记为不健康;如果持续 30 秒依旧接收不到心跳,就会直接把这个实例从服务列表当中删除。

服务端反向探测机制,则是由 Nacos 服务端主动向服务实例发起健康探测,默认探测的时间间隔为 20 秒。即便探测发现实例已经故障,只会将实例标记为不健康状态,并不会直接把实例从注册列表删除。客户端上报就如同员工主动汇报工作进度,服务端探测就相当于领导主动问询员工工作情况。

值得注意的是,这两种健康检查模式并不能够人为随意选择切换。健康检查的方式,是和 Nacos 当中的服务实例类型强绑定在一起的。Nacos 将注册进来的服务实例分为临时实例和非临时实例两种,不同实例会自动匹配对应的检测逻辑。

临时实例是 Nacos 的默认实例类型。当实例发生宕机,超过规定时间就会被 Nacos 从服务列表剔除,临时实例配套使用的就是客户端主动心跳上报机制。而非临时实例也叫永久实例,即便实例宕机下线,也不会被直接从服务列表移除,该类型实例采用服务端反向探测的方式做健康检查。想要把实例设置为非临时实例,可以在 yaml 配置中进行如下设置,重启服务之后即可生效。

spring: cloud: nacos: discovery: ephemeral: false

在实际使用的过程中会遇到实例类型切换报错的问题。如果一个服务已经注册为临时实例,在 IP 和端口不改变的情况下,直接修改配置改成非临时实例重启,会抛出异常。这是因为 Nacos 会持久保存服务实例的 IP、端口以及实例类型信息,不允许同一个服务在相同 IP 端口下混用临时和持久两种实例。解决该问题需要先停止 Nacos 服务,删除 data/protocol 目录下保存实例元数据的相关文件,再重新启动。

# 查找 Nacos 进程 ps -ef | grep nacos kill -9 PID # 删除 raft 文件夹 cd /usr/local/src/nacos/data/protocol rm -rf raft # 启动 Nacos cd /usr/local/src/nacos/bin sudo bash startup.sh -m standalone

还有一类常见现象:业务服务本身本地运行完全正常,但是 Nacos 控制台展示的实例健康状态却为 false。该问题大多出现在非临时实例场景下,是 Nacos 服务端反向探测失败导致,需要参考阿里云官方文档,排查持久实例的 HTTP 或者 TCP 探测相关规则。

二、Nacos 环境隔离

在企业实际开发当中,一套微服务项目通常会划分开发、测试、生产多套环境。开发环境供开发人员调试代码,日志级别较低,会保留大量调试信息;测试环境作为过渡,交由测试人员验证功能;生产环境面向真实用户,会关闭调试日志。不同环境的数据和服务需要相互隔离开来,不允许互相调用,而 Nacos 就提供了 Namespace 命名空间机制来实现这种环境隔离,处于不同命名空间下的服务互相不可见。

Nacos 初始状态下,所有注册的服务默认都归属于 public 这个内置命名空间。我们可以在 Nacos 控制台的命名空间页面,点击新增命名空间按钮,填写命名空间名称与描述信息完成创建。创建完成之后系统会生成一串唯一的 Namespace ID,后续代码配置需要使用这一串 ID,而不是我们填写的命名空间名称。

创建好命名空间之后,需要在微服务的配置文件中指定该命名空间 ID。对应的配置项为如下,该配置没有默认值,填入控制台复制得到的命名空间 ID,就可以把当前微服务注册到对应的命名空间当中。需要特别留意,服务注册的命名空间和配置中心的命名空间是两套独立配置,需要分开进行设置。

spring: cloud: nacos: discovery: namespace:

配置完成后可以对隔离效果进行测试。假设 product‑service 放在 public 命名空间,order‑service 配置注册到 dev 命名空间。启动两个服务之后,order‑service 在调用 product‑service 时,会抛出 “No instances available for product‑service” 的异常,找不到目标服务实例。只有把 product‑service 也修改 namespace 配置,注册到 dev 命名空间,二者才能够正常完成远程调用。

三、Nacos 配置中心

Nacos 除了可以充当注册中心、实现负载均衡之外,同时还具备完整的配置中心能力。命名空间在这里也能够发挥重要作用,很适合用来做不同环境之间的配置隔离,实现开发、测试、生产环境配置分开管理。

3.1. 解决痛点

  1. 修改配置需重启全量服务,多实例运维成本高;
  2. 本地配置文件多人开发易冲突;
  3. 统一集中管理所有微服务配置,修改实时生效无需重启。

3.2. 快速上手

  • 引入依赖:nacos-config + bootstrap
<dependency> <groupId>com.alibaba.cloud</groupId> <artifactId>spring-cloud-starter-alibaba-nacos-config</artifactId> </dependency> <!-- SpringCloud 2020.*之后版本需要引⼊bootstrap--> <dependency> <groupId>org.springframework.cloud</groupId> <artifactId>spring-cloud-starter-bootstrap</artifactId> </dependency>
  • 使用 bootstrap.yml 提前加载 Nacos 地址,优先级高于 application
spring: application: name: product-service profiles: active: @profile.name@ cloud: nacos: config: server-addr: 公网 IP namespace: 命名空间ID

bootstrap 文件加载时机更早,可以在微服务正式启动之前,优先从 Nacos 拉取配置,再和本地 application 配置做合并。配置中需要填写 Nacos 服务端地址,并且保证spring.application.name和控制台的 Data ID 保持一致。另外要区分两组地址配置,注册中心使用spring.cloud.nacos.discovery.server‑addr,配置中心使用 spring.cloud.nacos.config.server‑addr,二者相互独立。

  • 控制台新建配置

package com.yang.product.controller; import org.springframework.beans.factory.annotation.Value; import org.springframework.cloud.context.config.annotation.RefreshScope; import org.springframework.web.bind.annotation.RequestMapping; import org.springframework.web.bind.annotation.RestController; @RefreshScope @RestController public class NacosController { @Value("${nacos.config}") private String nacosConfig; @RequestMapping("/getConfig") public String getConfig() { return "从 Nacos 获取配置项 nacos.config:" + nacosConfig; } }

四、Nacos VS Eureka

4.1. 相同点

Nacos与Eureka都属于微服务领域的注册中心组件,二者存在部分相同的基础能力。二者都可以实现服务注册、服务实例拉取,能够满足微服务最基础的服务发现需求,这也是早期很多项目可以在两者之间做技术选型替换的重要原因。

4.2. 核心差异

在整体功能覆盖层面,两者有着明显的差距。Eureka的定位比较单一,仅仅只承担注册中心的职责,只负责服务注册与发现相关工作。而Nacos属于一体化微服务治理平台,除了基础的注册中心能力以外,还额外提供配置中心、流量管理、动态DNS服务等更多功能,一套组件就可以同时解决服务注册和配置管理两类核心问题。

从CAP理论的角度来看,两款组件的设计模式不一样。Eureka固定遵循AP原则,优先保证服务的可用性,放弃数据强一致性。Nacos则更加灵活,可以根据实例类型切换AP或者CP模式,当注册的是临时实例时走AP模式,注册非临时(持久)实例时走CP模式,在同一个Nacos集群当中,AP和CP两种模式还可以混合同时存在。

二者在服务发现的数据同步机制上也存在很大区别。Eureka采用拉模式,客户端会每隔30秒主动从服务端拉取服务实例信息,本地会缓存服务列表,因此服务上下线之后会存在一定的通知延迟。

Nacos 采用的是长连接推送模式。客户端和 Nacos 服务端会维持长连接,一旦服务实例发生新增、下线、状态变更,服务端会实时向订阅的客户端推送变更消息,不需要客户端轮询拉取,能够更快感知到服务的状态变化。日志中也可以看到对应的推送请求记录,直观体现推送机制的运行效果。

需要专业的网站建设服务?

联系我们获取免费的网站建设咨询和方案报价,让我们帮助您实现业务目标

立即咨询