Nacos 客户端版本从1.x 升级到 2.x 的排坑记

问题描述

应用引入 Nacos Config 配置管理功能,应用启动时读取 Nacos 配置中心的配置作为启动参数,其中包括数据源信息 url 。

当 Nacos 正在进行 GC 操作、无法响应客户端请求时,应用端刚启动时发送的登录认证请求 http://IP:PORT/nacos/v1/auth/users/login 就会报超时异常:

bash 复制代码
2023-11-29 18:08:13.067 [com.alibaba.nacos.client.config.security.updater] ERROR c.a.n.c.s.SecurityProxy - [login,154] - [SecurityProxy] login http request failed url: http://IP:PORT/nacos/v1/auth/users/login, params: {username=xx}, bodyMap: {password=xx}, errorMsg: Read timed out
2023-11-29 18:08:17.061 [main] ERROR c.a.n.c.c.i.ClientWorker - [getServerConfig,304] - [fixed-IP_PORT-public] [sub-server-error] no right, dataId=logging.yaml, group=DEFAULT_GROUP, tenant=public
2023-11-29 18:08:17.071 [main] ERROR c.a.c.n.c.NacosPropertySourceBuilder - [loadNacosData,101] - get data from Nacos error,dataId:logging.yaml 
com.alibaba.nacos.api.exception.NacosException: <html><body><h1>Whitelabel Error Page</h1><p>This application has no explicit mapping for /error, so you are seeing this as a fallback.</p><div id='created'>Wed Nov 29 18:08:16 CST 2023</div><div>There was an unexpected error (type=Forbidden, status=403).</div><div>unknown user!</div></body></html>
	at com.alibaba.nacos.client.config.impl.ClientWorker.getServerConfig(ClientWorker.java:306)

后面一些列的获取 bootstrap.yml 配置中的配置文件的请求都报未认证异常,应用程序因拿不到配置文件而走了 SpringBoot 的默认配置,SpringBoot 的数据源默认地址是 h2,数据源初始化异常,程序无法启动:

bash 复制代码
ERROR c.a.d.p.DruidDataSource - [init,936] - init datasource error, url: jdbc:h2:mem:9eede4b5-97dc-4d02-a202-7b3b4c6e8247;DB_CLOSE_DELAY=-1;DB_CLOSE_ON_EXIT=FALSE
java.sql.SQLException: connect error, url jdbc:h2:mem:9eede4b5-97dc-4d02-a202-7b3b4c6e8247;DB_CLOSE_DELAY=-1;DB_CLOSE_ON_EXIT=FALSE, driverClass oracle.jdbc.OracleDriver

Nacos 组件偶发的 GC 导致程序启动拿不到数据,这种现象是偶发的,有一个疑问,为什么 Nacos 配置认证失败时,没有去加载本地的快照信息呢? nacos server 部署的版本是 2.X ,但是客户端引入的 nacos 版本是 1.X 的,按网上的说法,思考升级 nacos-client 版本跟服务端一致能够解决这个问题呢。

还是一个问题就是经常出现 Nacos 不可用的异常:

bash 复制代码
java.net.ConnectException: no available server

想着升级一下来解决这个问题,本文记录升级客户端的坑。

升级 2.x 的客户端

官网给出的兼容 2.x 服务器的版本是 2021.1,用这个版本的客户端经常出现前文说的问题。支持 2.x 版本的 2022 及 2.2.X.RELEASE,选一个版本 2.2.9.RELEASE。

以为只是换个依赖包的问题,谁知道这里面有一个大坑,就是 nacos.config 配置用默认 namespace 时,不能在配置文件中进行设置,否则会获取不到配置。

客户端 spring-cloud-alibaba 升级为 2.2.9.RELEASE 之后,配置配置文件需要调整,应用使用默认命名空间时,必须注释掉 namespace: public 配置项:

xml 复制代码
    nacos:
      # nacos 服务器地址,依旧保持 8848 这个端口
      server-addr: IP:8848
      config:
        enabled: true
        username: xx
        password: xx
        # 引用的配置文件所属的命名空间,默认 public 时不能有该配置
#        namespace: public

2.x 客户端版本注意事项

《nacos 默认 namespace: public 拿不到数据》,搜到了这篇文章。根本的原因是在 Server 端的处理上,源码分析:

服务端是按上面的规则处理的,存储数据的 tenant_id 在 public 命名空间是是空的。而客户端请求代码中 tenant 就是 namespace, 当不指定时, params 里面没有 tenant 项, 只有在指定了namespace 时才会有这个请求参数,与服务端存储的不一致,导致怎么都获取不到数据。

所以注释掉 nacos.config.namespace 配置后,请求配置时 tenant 为空,才能拿到默认命名空间 public 的配置信息。

启示录

本周看到一个概念「知识错觉」,定义如下:

"知识错觉"(the illusion of knowledge)指的是,你自以为懂得或掌握了某种知识和技能,但是实际上并不懂。最近的一项研究表明,互联网可能会助长人们的"知识错觉",过度自信自己的技能水平。 研究人员让实验的参与者,重复观看某种技能的视频,例如投飞镖或者跳霹雳舞的视频,最多可以看20次。 看完以后,参与者需要预估一下,自己对这项技能的掌握程度。 大多数人表示,通过观看视频,他们已经一定程度上掌握了该项技能。而且,观看视频次数越多的人,回答越确定,自信心越强。 然后,每个人需要当众展示该项技能。结果令人非常失望,他们显然都没有掌握。研究人员说"他们的实际表现没有显示出任何学会的迹象。"

但其实,对技术领域来说,还不能用"知识错觉"来形容技术实践过程和教程之间不能顺利匹配的问题。很多技术的官方文档描述的很简单,实践时总会碰到各种诡异的问题,所以需要排坑!

本文 nacos 组件估计升级客户端还是解决不了问题,根源在于 nacos 面临的频繁的 GC 问题导致总会有一瞬间提供不了服务导致响应超时。即使微服务和 nacos 部署在同一台主机上,也没法避免。

哎!路漫漫啊呀......

相关推荐
Thomas.Sir1 小时前
第6课:Nacos核心原理 & 2025版适配SpringCloud环境搭建
spring cloud·微服务
需要82614 小时前
分布式事务:Seata AT/TCC/SAGA 的取舍与踩坑
java·spring boot·分布式·spring·spring cloud
无序的浪16 小时前
测试博客-基于微服务的在线判题系统
java·spring cloud·docker·微服务·测试·在线判题
需要82621 小时前
MySQL MVCC 与事务隔离级别:从一条 update 看版本链
java·数据库·spring boot·mysql·spring cloud
Rain的Java大神之路8 天前
如何快速上传10G文件
java·spring boot·redis·后端·mysql·spring cloud·面试
需要8268 天前
MySQL 索引 B+ 树与“查询为什么变慢了
java·spring boot·spring·spring cloud·tomcat
需要8268 天前
Arthas 一个命令排查线上问题
java·jvm·spring·spring cloud
苏渡苇9 天前
Spring Insight 里如何把 Span 画成瀑布时间线
后端·spring·spring cloud·springboot·监控·apm
叶总没有会9 天前
Nacos—注册中心
spring cloud·微服务
苏渡苇10 天前
Spring Insight 里如何把 Span 收成一条链路
spring boot·spring·spring cloud·系统监控·apm