nacos-naming 模块日志设计实现及思想

nacos作为注册中心,naming模块是其实现的主要位置,这里发现其日志实现比较有特色,简单讲一下。

一.日志类

模块位置如下:
不同的模块使用不通的日志路径做区分,直接上代码,

public class Loggers {

    public static final Logger PUSH = LoggerFactory.getLogger("com.alibaba.nacos.naming.push");

    public static final Logger CHECK_RT = LoggerFactory.getLogger("com.alibaba.nacos.naming.rt");

    public static final Logger SRV_LOG = LoggerFactory.getLogger("com.alibaba.nacos.naming.main");

    public static final Logger EVT_LOG = LoggerFactory.getLogger("com.alibaba.nacos.naming.event");

    public static final Logger RAFT = LoggerFactory.getLogger("com.alibaba.nacos.naming.raft");

    public static final Logger DISTRO = LoggerFactory.getLogger("com.alibaba.nacos.naming.distro");

    public static final Logger PERFORMANCE_LOG = LoggerFactory.getLogger("com.alibaba.nacos.naming.performance");

    public static void setLogLevel(String logName, String level) {

        switch (logName) {
            case "naming-push":
                ((ch.qos.logback.classic.Logger) PUSH).setLevel(Level.valueOf(level));
                break;
            case "naming-rt":
                ((ch.qos.logback.classic.Logger) CHECK_RT).setLevel(Level.valueOf(level));
                break;
            case "naming-server":
                ((ch.qos.logback.classic.Logger) SRV_LOG).setLevel(Level.valueOf(level));
                break;
            case "naming-event":
                ((ch.qos.logback.classic.Logger) EVT_LOG).setLevel(Level.valueOf(level));
                break;
            case "naming-raft":
                ((ch.qos.logback.classic.Logger) RAFT).setLevel(Level.valueOf(level));
                break;
            case "naming-distro":
                ((ch.qos.logback.classic.Logger) DISTRO).setLevel(Level.valueOf(level));
                break;
            case "naming-performance":
                ((ch.qos.logback.classic.Logger) PERFORMANCE_LOG).setLevel(Level.valueOf(level));
                break;
            default:
                break;
        }

    }
}

二.日志级别动态控制

后面通过暴漏的controller接口控制每个的日志的等级

	@RequestMapping("/nacos/v1/ns/operator")
	public Class OperatorController {
		 @PutMapping("/log")
   		 public String setLogLevel(@RequestParam String logName, @RequestParam String logLevel) {
        	Loggers.setLogLevel(logName, logLevel);
         return "ok";
    	}
	}

通过这种方式可以控制某个模块下日志的打印级别,方便在排查问题的时候动态的调整日志的输出级别。

Caused by: org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'distroFilterRegistration' defined in class path resource [com/alibaba/nacos/naming/web/NamingConfig.class]: Bean instantiation via factory method failed; nested exception is org.springframework.beans.BeanInstantiationException: Failed to instantiate [org.springframework.boot.web.servlet.FilterRegistrationBean]: Factory method 'distroFilterRegistration' threw exception; nested exception is org.springframework.beans.factory.UnsatisfiedDependencyException: Error creating bean with name 'distroFilter': Unsatisfied dependency expressed through field 'distroMapper'; nested exception is org.springframework.beans.factory.UnsatisfiedDependencyException: Error creating bean with name 'distroMapper' defined in URL [jar:file:/opt/package/aitransfer/16K_GPU_A/aizt/nacos/target/nacos-server.jar!/BOOT-INF/lib/nacos-naming-2.2.3.jar!/com/alibaba/nacos/naming/core/DistroMapper.class]: Unsatisfied dependency expressed through constructor parameter 0; nested exception is org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'serverMemberManager' defined in URL [jar:file:/opt/package/aitransfer/16K_GPU_A/aizt/nacos/target/nacos-server.jar!/BOOT-INF/lib/nacos-core-2.2.3.jar!/com/alibaba/nacos/core/cluster/ServerMemberManager.class]: Bean instantiation via constructor failed; nested exception is org.springframework.beans.BeanInstantiationException: Failed to instantiate [com.alibaba.nacos.core.cluster.ServerMemberManager]: Constructor threw exception; nested exception is ErrCode:500, ErrMsg:jmenv.tbsite.net 什么原因导致的报错
最新发布
07-16
<think>我们正在处理一个关于Spring Boot应用启动失败的问题,具体错误是在Nacos 2.2.3启动日志中出现的Bean创建异常:`Caused by: org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'distroFilterRegistration'`。 首先,我们需要理解这个错误的背景。在Nacos中,`distroFilterRegistration`是一个与Nacos集群一致性协议(Distro协议)相关的过滤器注册Bean。Distro协议是Nacos用于临时实例(非持久化实例)的一致性协议。这个Bean的创建失败通常意味着在初始化过程中出现了问题。 ### 错误原因分析 1. **依赖缺失或版本冲突**:可能是某个依赖的类或Bean没有正确注入,或者版本不兼容。 2. **配置问题**:Nacos的相关配置可能不正确,导致在创建Bean时无法获取必要的配置信息。 3. **环境问题**:例如,网络问题导致集群节点间通信失败,或者资源(如内存、端口)不足。 4. **代码缺陷**:在特定版本的Nacos中可能存在Bug。 ### 解决步骤 #### 1. 检查依赖 确保你的项目中使用的Nacos客户端和服务端版本一致且兼容。在Spring Boot项目中,通常通过`spring-cloud-starter-alibaba-nacos-discovery`和`spring-cloud-starter-alibaba-nacos-config`引入Nacos。检查这些依赖的版本是否与Nacos服务端版本兼容。 例如,对于Nacos 2.2.3,建议使用Spring Cloud Alibaba 2022.0.0.0或更高版本。你可以参考[Spring Cloud Alibaba版本说明](https://github.com/alibaba/spring-cloud-alibaba/wiki/版本说明)。 #### 2. 检查配置 在application.properties或application.yml中,检查Nacos相关的配置是否正确,特别是: ```properties spring.cloud.nacos.discovery.server-addr=127.0.0.1:8848 spring.cloud.nacos.config.server-addr=127.0.0.1:8848 ``` 确保Nacos服务端地址正确,并且服务端正在运行。 #### 3. 查看完整日志 查看完整的错误堆栈,定位更具体的错误原因。在`BeanCreationException`的堆栈中,通常会有一个根本原因(`root cause`),它可能指示了更具体的问题,比如: - 某个类找不到(`ClassNotFoundException`) - 某个方法调用失败(如连接超时) - 资源访问失败(如无法读取配置文件) 例如,如果根本原因是连接Nacos服务器超时,那么需要检查网络连接和Nacos服务状态。 #### 4. 升级版本 如果确认是Nacos的Bug,可以尝试升级到更高版本。Nacos 2.2.3可能存在已知问题,可以查看Nacos的[Release Notes](https://github.com/alibaba/nacos/releases)和[Issues](https://github.com/alibaba/nacos/issues)来确认。 #### 5. 检查集群配置 如果使用Nacos集群,确保集群配置正确,节点之间能够互相通信。检查`cluster.conf`文件中的节点地址是否正确,以及防火墙设置是否允许节点间通信。 #### 6. 调试代码 如果以上步骤无法解决问题,可以尝试在本地调试Nacos源码。根据错误堆栈,定位到创建`distroFilterRegistration`的地方(通常在`DistroFilterConfig`类中),并逐步调试。 ### 示例解决方案 假设错误是由于依赖冲突导致的,我们可以通过Maven的依赖树分析冲突: ```bash mvn dependency:tree -Dincludes=com.alibaba.nacos ``` 然后排除冲突的依赖。 ### 总结 处理这类启动错误的关键是: 1. 仔细阅读错误堆栈,定位根本原因。 2. 检查依赖、配置和环境。 3. 查阅官方文档和社区已知问题。 4. 升级或回退版本以规避已知Bug。 [^1]: 参考自Nacos官方文档:https://nacos.io/zh-cn/docs/quick-start.html §§相关问题§§ 1. 如何排查Spring Boot启动时的Bean创建异常? 2. Nacos集群配置需要注意哪些问题? 3. 如何解决Spring Cloud Alibaba与Nacos版本兼容性问题? 4. 在Nacos中,Distro协议的作用是什么?</think>### Nacos启动时`distroFilterRegistration` Bean创建异常分析 该错误表明Nacos在启动时无法创建名为`distroFilterRegistration`的Bean。这是Nacos集群通信模块的关键组件,负责处理Distro协议(Nacos自研的AP分布式协议)的网络通信。以下是常见原因和解决方案: #### 常见原因分析 1. **依赖冲突** Spring Boot/Nacos版本不兼容(特别是Spring Cloud Alibaba版本) ```xml <!-- 典型版本要求 --> <dependency> <groupId>com.alibaba.cloud</groupId> <artifactId>spring-cloud-starter-alibaba-nacos-discovery</artifactId> <version>2022.0.0.0</version> <!-- 需匹配Nacos 2.2.3 --> </dependency> ``` 2. **配置缺失** `application.yml`中缺少必要配置: ```yaml spring: cloud: nacos: discovery: server-addr: 127.0.0.1:8848 config: auto-refresh: true ``` 3. **网络问题** - 集群节点间端口未开放(默认7848/9848) - 防火墙阻止了`7848`(RAFT)和`9848`(gRPC)端口通信 4. **资源冲突** - 端口占用(检查`8848`/`9848`) - 文件锁冲突(Linux系统`/proc/sys/kernel/pid_max`设置) #### 解决方案 1. **验证版本兼容性** 使用兼容组合: ```markdown Nacos 2.2.3 → Spring Boot 2.7.x → Spring Cloud 2021.0.5 → Spring Cloud Alibaba 2021.0.5.0 ``` 2. **清理依赖冲突** 执行Maven命令检查冲突: ```bash mvn dependency:tree -Dincludes=com.alibaba.nacos ``` 排除冲突依赖: ```xml <exclusions> <exclusion> <groupId>org.apache.tomcat.embed</groupId> <artifactId>tomcat-embed-core</artifactId> </exclusion> </exclusions> ``` 3. **检查集群配置** 确认`cluster.conf`格式正确(每行一个IP:PORT): ```plaintext 192.168.1.101:8848 192.168.1.102:8848 ``` 4. **启用调试日志** 在`application.yml`添加: ```yaml logging: level: com.alibaba.nacos: DEBUG org.springframework.beans: TRACE ``` 5. **文件权限修复** Linux系统执行: ```bash chmod -R 755 /home/nacos # 确保data和logs目录可写 ``` #### 核心代码定位 异常通常发生在Distro组件初始化时: ```java // 源码位置:com.alibaba.nacos.naming.web.DistroFilterConfig @Bean public FilterRegistrationBean distroFilterRegistration() { FilterRegistrationBean<DistroFilter> registration = new FilterRegistrationBean<>(); registration.setFilter(new DistroFilter()); // 此处可能因依赖缺失失败 registration.addUrlPatterns("/*"); registration.setName("distroFilter"); return registration; } ``` > **注意**:若使用Docker部署,需添加`-e NACOS_SERVER_PORT=8848 -e NACOS_APPLICATION_PORT=8848`环境变量[^1]
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值