大家好,我是烤鸭:

    nacos 真的是有点意思,有时候哪怕某个jar包版本冲突了都可能导致莫名其妙的错误,源码走一波吧。

当前版本

org.springframework.boot

spring-boot-dependencies

2.2.6.RELEASE

pom

import

org.springframework.cloud

spring-cloud-dependencies

Hoxton.SR12

pom

import

com.alibaba.cloud

spring-cloud-starter-alibaba-nacos-config

2.2.1.RELEASE

报错日志

com.alibaba.nacos.api.exception.NacosException:

Whitelabel Error Page

This application has no explicit mapping for /error, so you are seeing this as a fallback.

Sat May 14 06:51:53 CST 2022
There was an unexpected error (type=Forbidden, status=403).
unknown user!

at com.alibaba.nacos.client.config.impl.ClientWorker.getServerConfig(ClientWorker.java:262)

at com.alibaba.nacos.client.config.NacosConfigService.getConfigInner(NacosConfigService.java:143)

at com.alibaba.nacos.client.config.NacosConfigService.getConfig(NacosConfigService.java:92)

at com.alibaba.cloud.nacos.client.NacosPropertySourceBuilder.loadNacosData(NacosPropertySourceBuilder.java:85)

at com.alibaba.cloud.nacos.client.NacosPropertySourceBuilder.build(NacosPropertySourceBuilder.java:74)

at com.alibaba.cloud.nacos.client.NacosPropertySourceLocator.loadNacosPropertySource(NacosPropertySourceLocator.java:204)

at com.alibaba.cloud.nacos.client.NacosPropertySourceLocator.loadNacosDataIfPresent(NacosPropertySourceLocator.java:191)

at com.alibaba.cloud.nacos.client.NacosPropertySourceLocator.loadNacosConfiguration(NacosPropertySourceLocator.java:161)

at com.alibaba.cloud.nacos.client.NacosPropertySourceLocator.loadExtConfiguration(NacosPropertySourceLocator.java:129)

at com.alibaba.cloud.nacos.client.NacosPropertySourceLocator.locate(NacosPropertySourceLocator.java:102)

at org.springframework.cloud.bootstrap.config.PropertySourceLocator.locateCollection(PropertySourceLocator.java:52)

at org.springframework.cloud.bootstrap.config.PropertySourceLocator.locateCollection(PropertySourceLocator.java:47)

at org.springframework.cloud.bootstrap.config.PropertySourceBootstrapConfiguration.initialize(PropertySourceBootstrapConfiguration.java:101)

at org.springframework.boot.SpringApplication.applyInitializers(SpringApplication.java:623)

at org.springframework.boot.SpringApplication.prepareContext(SpringApplication.java:367)

at org.springframework.boot.SpringApplication.run(SpringApplication.java:311)

at org.springframework.boot.SpringApplication.run(SpringApplication.java:1215)

at org.springframework.boot.SpringApplication.run(SpringApplication.java:1204)

at com.xxx.xxx.task.XxxTaskApplication.main(XxxTaskApplication.java:11)

问题猜想

nacos-client 1.2.0 以下的官方bug

https://blog.csdn.net/qq_35337554/article/details/104914397

这种问题大概率是版本问题,springboot/cloud/alibaba-cloud 参考版本。 https://blog.csdn.net/qq_38637558/article/details/114448690

client版本和server版本也要对的上,要注意下,不能盲目升client的版本,client和server 参考版本。

https://www.jianshu.com/p/df88e1967036

看看源码

如果上面的博客都看过了,还没解决问题,可能跟我的问题相似。

我们看下报错地方的源码, 为什么会报错。

ClientWorker 中 getServerConfig方法的 agent.httpGet 返回 403

public String[] getServerConfig(String dataId, String group, String tenant, long readTimeout)

throws NacosException {

String[] ct = new String[2];

if (StringUtils.isBlank(group)) {

group = Constants.DEFAULT_GROUP;

}

HttpResult result = null;

try {

List params = null;

if (StringUtils.isBlank(tenant)) {

params = new ArrayList(Arrays.asList("dataId", dataId, "group", group));

} else {

params = new ArrayList(Arrays.asList("dataId", dataId, "group", group, "tenant", tenant));

}

result = agent.httpGet(Constants.CONFIG_CONTROLLER_PATH, null, params, agent.getEncode(), readTimeout);

} catch (IOException e) {

// 忽略无关代码

}

switch (result.code) {

// 忽略无关代码

case HttpURLConnection.HTTP_FORBIDDEN: {

LOGGER.error("[{}] [sub-server-error] no right, dataId={}, group={}, tenant={}", agent.getName(), dataId,

group, tenant);

throw new NacosException(result.code, result.content);

}

default: {

// 忽略无关代码

}

}

}

发现agent中的请求accessToken是null

accessToken 是项目启动后登录nacos返回的

这个就是 nacos-1.2.1 的源码,记住下面这个没有打印日志的异常。

SecurityProxy

public boolean login(List servers) {

try {

if ((System.currentTimeMillis() - lastRefreshTime) < TimeUnit.SECONDS.toMillis(tokenTtl - tokenRefreshWindow)) {

return true;

}

for (String server : servers) {

if (login(server)) {

lastRefreshTime = System.currentTimeMillis();

return true;

}

}

} catch (Throwable ignore) {

}

return false;

}

进 login 方法里看,我擦,报红了。

问题解决

Charsets 来自

import org.apache.commons.codec.Charsets;

pom

commons-codec

commons-codec

1.4

问题找到了, 我们项目用的 commons-codec 版本是1.4 ,已经没有这个类了,降到 1.13 没问题了

总结

一个简单的问题搞这么复杂,翻了n多博客,都没找到原因。

编译没报错,启动时候报错日志也没有,到请求nacos的时候,变成403了,这尼玛怎么找。

阿里开源的果然很坑,不过 2.0 据说优化了很多内容,性能也有很大提升。

伟大的开源都少不了大家的踩坑和pr,希望国产开源也越来越好吧,而不是为了什么OKR。

好文推荐

评论可见,请评论后查看内容,谢谢!!!
 您阅读本篇文章共花了: