记一次诡异的空指针

接到一个问题,说服务启动后偶尔会有空指针的问题。偶现。

背景

项目是 SpringBoot 项目,

按报错,是 service 注入为空,然后在执行时就空指针了。

@Service("xxxService")
public class xxxService {

    @Autowired
    AService aService;


    public void exec(){
        aService.run();//这里抛了空指针
    }
}

问题表象

偶现的空指针,在服务启动后,有时ok,有时空指针。

问题排查

首先想到的是启动有异常了。Spring Bean 初始化失败了。

登上服务器,启动异常的情况下,看了下启动日志。没有异常。

但是很明显的看到另一个问题。

服务启动时。 Spring Bean 执行了两次实例化 。

问题一下子就明了了。

问题

查看了 main 方法。

public class SpringMain{
    public static void main(String[] args){
        //.....略过中间逻辑

        application.run();
        //......略过中间逻辑
        application.run();
    }
}

明显程序 run 了两次。bean 实例化了两次。

那么为什么 Spring 实例化第二次,就不再初始化 bean 了呢??第二次实例化的 bean 就是个 null 了呢?

原因

这就是 Spring 初始化的流程得了解 。

这里 run 了两次,但 run 的是同一个 Spring 容器,同一个 Spring 容器内会去加载 Bean。

但会判断下 Bean 是否已经初始化了 。 如果已经初始化了,就不再初始化了。

解决

去掉一个 run()

总结

新手们还是要多解一些原理。写代码会写,但定位问题也很重要,

这么明显的执行了两次实例化竟然看不见。。。

原文地址:https://www.cnblogs.com/ElEGenT/p/12708742.html