目录

Spring Bean的生命周期

谈一谈Sping Bean的生命周期?

Spring Bean 生命周期核心概念

简单来说,Spring Bean 的生命周期 就是 Bean 从「被 Spring 容器创建」到「最终被销毁」的全流程。Spring 容器会接管 Bean 的创建、初始化、依赖注入、使用、销毁等所有环节,我们可以通过各种扩展点(如接口、注解)介入这个流程,实现自定义逻辑。

Spring Bean 完整生命周期(8 个核心阶段)

Bean生命周期:

代码示例:

示例Bean:

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
import org.springframework.beans.BeansException;
import org.springframework.beans.factory.*;
import org.springframework.context.ApplicationContext;
import org.springframework.context.ApplicationContextAware;
import javax.annotation.PostConstruct;
import javax.annotation.PreDestroy;

/**
 * 自定义 Bean,实现所有生命周期扩展接口
 */
public class UserBean implements BeanNameAware, BeanFactoryAware, ApplicationContextAware, InitializingBean, DisposableBean {

    // 模拟依赖注入的属性
    private String username;

    // ------------------- 阶段1:实例化 Bean -------------------
    // Spring 通过反射调用无参构造器创建 Bean 实例(开发者无需干预)
    public UserBean() {
        System.out.println("【阶段1】实例化 Bean:调用无参构造器");
    }

    // ------------------- 阶段2:设置 Bean 属性(依赖注入) -------------------
    // Spring 自动为属性赋值(setter注入/字段注入)
    public void setUsername(String username) {
        this.username = username;
        System.out.println("【阶段2】设置 Bean 属性:username = " + username);
    }

    // ------------------- 阶段3:BeanNameAware 接口 -------------------
    // 注入当前 Bean 在容器中的名称
    @Override
    public void setBeanName(String name) {
        System.out.println("【阶段3】BeanNameAware:Bean 名称 = " + name);
    }

    // ------------------- 阶段4:BeanFactoryAware 接口 -------------------
    // 注入当前 Bean 所属的 BeanFactory
    @Override
    public void setBeanFactory(BeanFactory beanFactory) throws BeansException {
        System.out.println("【阶段4】BeanFactoryAware:BeanFactory = " + beanFactory.getClass().getSimpleName());
    }

    // ------------------- 阶段5:ApplicationContextAware 接口 -------------------
    // 注入 Spring 应用上下文(若依框架中常用此接口获取容器中的 Bean)
    @Override
    public void setApplicationContext(ApplicationContext applicationContext) throws BeansException {
        System.out.println("【阶段5】ApplicationContextAware:ApplicationContext = " + applicationContext.getClass().getSimpleName());
    }

    // ------------------- 阶段6:BeanPostProcessor 前置处理 -------------------
    // 需自定义 BeanPostProcessor 实现,见下方代码

    // ------------------- 阶段7:初始化(@PostConstruct / InitializingBean) -------------------
    // 方式1:@PostConstruct 注解(JSR-250标准,推荐)
    @PostConstruct
    public void postConstruct() {
        System.out.println("【阶段7-1】@PostConstruct:初始化 Bean");
    }

    // 方式2:实现 InitializingBean 接口
    @Override
    public void afterPropertiesSet() throws Exception {
        System.out.println("【阶段7-2】InitializingBean:afterPropertiesSet 方法执行");
    }

    // 方式3:自定义 init-method(XML/注解配置,见配置类)
    public void customInitMethod() {
        System.out.println("【阶段7-3】自定义 init-method:初始化逻辑");
    }

    // ------------------- 阶段8:BeanPostProcessor 后置处理 -------------------
    // 需自定义 BeanPostProcessor 实现,见下方代码

    // ------------------- 阶段9:Bean 就绪,对外提供服务 -------------------
    public void doBusiness() {
        System.out.println("【阶段9】Bean 就绪:执行业务逻辑,username = " + username);
    }

    // ------------------- 阶段10:销毁(@PreDestroy / DisposableBean) -------------------
    // 方式1:@PreDestroy 注解(JSR-250标准,推荐)
    @PreDestroy
    public void preDestroy() {
        System.out.println("【阶段10-1】@PreDestroy:销毁前处理");
    }

    // 方式2:实现 DisposableBean 接口
    @Override
    public void destroy() throws Exception {
        System.out.println("【阶段10-2】DisposableBean:destroy 方法执行");
    }

    // 方式3:自定义 destroy-method(XML/注解配置,见配置类)
    public void customDestroyMethod() {
        System.out.println("【阶段10-3】自定义 destroy-method:销毁逻辑");
    }
}

自定义 BeanPostProcessor(核心扩展点)

BeanPostProcessor 是 Spring 生命周期中最强大的扩展点,可对所有 Bean 进行前置 / 后置处理(若依框架中的权限切面、日志切面底层都依赖类似机制):

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
import org.springframework.beans.BeansException;
import org.springframework.beans.factory.config.BeanPostProcessor;
import org.springframework.stereotype.Component;

/**
 * 自定义 BeanPostProcessor,拦截所有 Bean 的初始化前后
 */
@Component
public class CustomBeanPostProcessor implements BeanPostProcessor {

    // 初始化前处理(阶段6)
    @Override
    public Object postProcessBeforeInitialization(Object bean, String beanName) throws BeansException {
        if ("userBean".equals(beanName)) { // 仅处理指定 Bean
            System.out.println("【阶段6】BeanPostProcessor 前置处理:" + beanName);
        }
        return bean; // 必须返回 Bean 实例,否则会导致 Bean 丢失
    }

    // 初始化后处理(阶段8)
    @Override
    public Object postProcessAfterInitialization(Object bean, String beanName) throws BeansException {
        if ("userBean".equals(beanName)) {
            System.out.println("【阶段8】BeanPostProcessor 后置处理:" + beanName);
        }
        return bean;
    }
}

配置类(注册 Bean + 指定初始化 / 销毁方法)

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

@Configuration
public class BeanConfig {

    @Bean(initMethod = "customInitMethod", destroyMethod = "customDestroyMethod")
    public UserBean userBean() {
        UserBean userBean = new UserBean();
        userBean.setUsername("admin"); // 模拟依赖注入
        return userBean;
    }
}

测试类(触发生命周期)

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
import org.springframework.context.annotation.AnnotationConfigApplicationContext;

public class BeanLifecycleTest {
    public static void main(String[] args) {
        // 1. 创建 Spring 容器,加载配置
        AnnotationConfigApplicationContext context = new AnnotationConfigApplicationContext(BeanConfig.class);

        // 2. 获取 Bean 并执行业务逻辑
        UserBean userBean = context.getBean(UserBean.class);
        userBean.doBusiness();

        // 3. 关闭容器,触发 Bean 销毁
        context.close();
    }
}

输出结果

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
【阶段1】实例化 Bean:调用无参构造器
【阶段2】设置 Bean 属性:username = admin
【阶段3】BeanNameAware:Bean 名称 = userBean
【阶段4】BeanFactoryAware:BeanFactory = DefaultListableBeanFactory
【阶段5】ApplicationContextAware:ApplicationContext = AnnotationConfigApplicationContext
【阶段6】BeanPostProcessor 前置处理:userBean
【阶段7-1】@PostConstruct:初始化 Bean
【阶段7-2】InitializingBean:afterPropertiesSet 方法执行
【阶段7-3】自定义 init-method:初始化逻辑
【阶段8】BeanPostProcessor 后置处理:userBean
【阶段9】Bean 就绪:执行业务逻辑,username = admin
【阶段10-1】@PreDestroy:销毁前处理
【阶段10-2】DisposableBean:destroy 方法执行
【阶段10-3】自定义 destroy-method:销毁逻辑

关键补充(结合实际开发)

不同初始化 / 销毁方式的优先级

  1. 初始化优先级:@PostConstruct > InitializingBean.afterPropertiesSet() > 自定义 init-method

  2. 销毁优先级:@PreDestroy > DisposableBean.destroy() > 自定义 destroy-method

  3. 推荐使用 @PostConstruct 和 @PreDestroy(解耦 Spring 接口,符合开闭原则)。

原型 Bean 的生命周期差异

  1. 原型 Bean 由容器创建实例、注入属性、执行初始化,但不管理销毁阶段(容器关闭时不会调用 destroy 方法);

  2. 若需销毁原型 Bean,需手动调用销毁方法。

若依框架中的生命周期应用

  1. ApplicationContextAware:若依框架中的 SpringUtils 工具类实现此接口,用于手动获取容器中的 Bean,解决循环依赖;

  2. @PostConstruct:若依的定时任务、缓存初始化等逻辑,常放在 @PostConstruct 方法中,确保 Bean 初始化完成后执行;

  3. BeanPostProcessor:若依的权限注解解析、数据权限切面等,底层依赖 BeanPostProcessor 扩展。

核心原理(为什么能控制生命周期?)

Spring 容器通过 BeanFactory(核心是 DefaultListableBeanFactory)管理 Bean 生命周期:

实例化:通过反射创建 Bean 实例(AbstractAutowireCapableBeanFactory.createBeanInstance);

属性填充:解析依赖,注入属性(populateBean);

初始化:执行各类初始化方法(initializeBean);

销毁:容器关闭时,遍历单例 Bean 执行销毁方法(destroySingletons)。

总结

核心流程:Spring Bean 生命周期可概括为「实例化 → 属性注入 → 感知容器 → 前置处理 → 初始化 → 后置处理 → 就绪使用 → 销毁」8 个核心阶段;

扩展方式:常用 @PostConstruct/@PreDestroy 做初始化 / 销毁,BeanPostProcessor 做全局 Bean 增强,ApplicationContextAware 手动获取容器;

实战要点:若依框架中大量使用 ApplicationContextAware 和 @PostConstruct,掌握这些扩展点能灵活定制 Bean 行为。

理解 Bean 生命周期,能帮你解决「Bean 初始化时机不对」「依赖注入失败」「销毁资源未释放」等实际开发问题,也是深入学习 Spring 核心原理的基础