一文彻底搞懂 Spring Bean 的生命周期与扩展机制

Spring 的核心是 IoC(Inversion of Control,控制反转)容器。
它负责管理 Bean 的创建、注入、初始化与销毁。
理解 Spring Bean 的生命周期,是掌握 Spring 框架原理的关键一步。

一、什么是 Bean 的生命周期?

所谓 Bean 的生命周期(Bean Lifecycle),就是一个 Bean 从“定义”到“销毁”的完整过程。
Spring 容器会自动接管 Bean 的整个生命周期:

  • 负责对象的创建(实例化)
  • 属性注入(依赖关系)
  • 初始化(执行自定义逻辑)
  • 销毁(资源清理)

Spring 还在每个阶段都暴露了大量 扩展点(Extension Point),
让我们能在关键节点上插入自定义逻辑,例如日志打印、Bean 修改、自动代理等。

二、Spring Bean 生命周期六大阶段

下面是 Spring Bean 生命周期的完整流程图思维:
定义 → 实例化 → 注入 → 感知 → 初始化 → 销毁

① Bean 定义阶段(Definition Phase)

主要动作:

Spring 从配置源(XML、注解、Java Config)中读取 Bean 信息。

生成 BeanDefinition,其中包含类名、作用域、依赖、初始化方法、销毁方法等元数据。

关键扩展点:

BeanDefinitionRegistryPostProcessor

BeanFactoryPostProcessor

典型用途:

动态注册 Bean

修改 Bean 的定义(如数据源动态切换)

影响范围:

通常作用于整个容器中的多个 Bean

示例
@Component
public class CustomBeanFactoryPostProcessor implements BeanFactoryPostProcessor {
    @Override
    public void postProcessBeanFactory(ConfigurableListableBeanFactory beanFactory) {
        BeanDefinition bd = beanFactory.getBeanDefinition("userService");
        bd.getPropertyValues().add("level", "VIP");
        System.out.println("✅ 修改了 userService 的默认属性 level=VIP");
    }
}

② Bean 实例化阶段(Instantiation Phase)

主要动作:

Spring 根据 BeanDefinition 反射创建 Bean 实例。

此时仅完成 new 操作,还没有注入属性。

关键扩展点:

InstantiationAwareBeanPostProcessor#postProcessBeforeInstantiation

InstantiationAwareBeanPostProcessor#postProcessAfterInstantiation

典型用途:

替换原始 Bean(AOP 可以介入,但默认不在这里执行)

跳过默认实例化流程

影响范围:

单个 Bean

示例
@Component
public class CustomInstantiationAwareProcessor extends InstantiationAwareBeanPostProcessorAdapter {
    @Override
    public Object postProcessBeforeInstantiation(Class<?> beanClass, String beanName) {
        if (beanClass == UserService.class) {
            System.out.println("⚙️ 正在准备实例化 UserService...");
        }
        return null; // 返回非 null 可以替代默认实例
    }
}

③ 属性注入阶段(Populate Properties Phase)

主要动作:

Spring 为 Bean 注入依赖(@Autowired、@Value、@Resource 等)

处理循环依赖(单例 Bean)

关键扩展点:

InstantiationAwareBeanPostProcessor#postProcessProperties

典型用途:

修改或校验属性值

动态调整依赖

影响范围:

单个 Bean

示例
@Component
public class MessageService {

    @Value("${msg.sender:system}") // 注入配置属性
    private String sender;

    @Autowired
    private MessageRepository messageRepository; // 注入依赖 Bean

    public void send(String to, String content) {
        messageRepository.save(sender, to, content);
        System.out.println("📨 消息已发送:" + sender + " -> " + to);
    }
}

④ 感知接口回调阶段(Aware Interfaces Phase)

主要动作:

如果 Bean 实现了某些 Aware 接口,Spring 会主动注入容器对象,让 Bean 感知运行环境。

常见接口:

接口 作用
BeanNameAware 获取当前 Bean 的名称
BeanFactoryAware 获取 BeanFactory 实例
ApplicationContextAware 获取 ApplicationContext
EnvironmentAware 获取运行环境
ResourceLoaderAware 获取资源加载器

典型用途:

获取上下文对象

动态加载配置或资源

影响范围:

单个 Bean

示例
@Component
public class BeanFetcher implements ApplicationContextAware {
    private static ApplicationContext context;

    @Override
    public void setApplicationContext(ApplicationContext ctx) {
        context = ctx;
    }

    public static <T> T getBean(Class<T> type) {
        return context.getBean(type);
    }
}

⑤ 初始化阶段(Initialization Phase)

主要动作:

Bean 已完成依赖注入,此阶段执行各种初始化逻辑。

执行顺序:

1️⃣ BeanPostProcessor#postProcessBeforeInitialization()
2️⃣ 执行初始化方法:

@PostConstruct

InitializingBean#afterPropertiesSet()

XML 或 JavaConfig 中的 init-method
3️⃣ BeanPostProcessor#postProcessAfterInitialization()(AOP 代理点)

常见用途:

初始化连接池、缓存等资源

对 Bean 做额外包装或增强(AOP、事务、异步等)

影响范围:

单个 Bean(但增强逻辑可能影响其他 Bean 的代理)

示例
//BeanPostProcessor 实现自动代理增强(AOP 前奏)
@Component
public class TimingPostProcessor implements BeanPostProcessor {

    @Override
    public Object postProcessAfterInitialization(Object bean, String beanName) {
        if (bean instanceof OrderService target) {
            return Proxy.newProxyInstance(
                bean.getClass().getClassLoader(),
                bean.getClass().getInterfaces(),
                (proxy, method, args) -> {
                    long start = System.currentTimeMillis();
                    Object result = method.invoke(target, args);
                    long cost = System.currentTimeMillis() - start;
                    System.out.println("⏱️ 方法 " + method.getName() + " 执行耗时:" + cost + "ms");
                    return result;
                });
        }
        return bean;
    }
}

⑥ 销毁阶段(Destruction Phase)

主要动作:

容器关闭或 Bean 被移除时,Spring 调用销毁逻辑。

执行顺序:

1️⃣ @PreDestroy
2️⃣ DisposableBean#destroy()
3️⃣ XML 或 JavaConfig 中的 destroy-method

常见用途:

关闭连接、释放资源、停止线程池等

影响范围:

单个 Bean

示例
//关闭线程池或连接池
@Component
public class ThreadPoolManager implements DisposableBean {
    private final ExecutorService executor = Executors.newFixedThreadPool(2);

    public void submitTask(Runnable task) {
        executor.submit(task);
    }

    @Override
    public void destroy() {
        System.out.println("🧹 销毁前:准备关闭线程池...");
        executor.shutdown();
        System.out.println("💀 销毁完成:线程池关闭。");
    }
}

三、生命周期与扩展点对照表

阶段 主要动作 关键扩展点 示例 常见用途
① 定义 解析 BeanDefinition BeanFactoryPostProcessor 修改 Bean 属性 动态 Bean 注册
② 实例化 new 对象 InstantiationAwareBeanPostProcessor 拦截 Bean 创建 创建代理
③ 属性注入 注入依赖 @Autowired, @Value 注入 MessageRepository 自动装配
④ 感知阶段 Aware 回调 各类 *Aware 接口 获取上下文 获取容器信息
⑤ 初始化 初始化逻辑 @PostConstruct, BeanPostProcessor 建立连接、增强 Bean 初始化资源
⑥ 销毁 资源清理 @PreDestroy, DisposableBean 关闭线程池、清理缓存 释放资源

四、总结

一句话记忆:

定义 → 实例化 → 注入 → 感知 → 初始化 → 销毁

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
【社区内容提示】社区部分内容疑似由AI辅助生成,浏览时请结合常识与多方信息审慎甄别。
平台声明:文章内容(如有图片或视频亦包括在内)由作者上传并发布,文章内容仅代表作者本人观点,简书系信息发布平台,仅提供信息存储服务。

友情链接更多精彩内容