全部学科
NodeJS全栈
nodejs
Python全栈
python
小程序首页
📅 2026-05-18 6 分钟 ✍️ juanwangdev

InitializingBean 和 DisposableBean

这两个接口定义Bean的初始化和销毁回调。

接口定义

Java
public interface InitializingBean {
    void afterPropertiesSet() throws Exception;
}

public interface DisposableBean {
    void destroy() throws Exception;
}

执行时机

初始化时机

Java
┌─────────────────────────────────────┐
│  Bean实例化                          │
├─────────────────────────────────────┤
│  属性注入                            │
├─────────────────────────────────────┤
│  Aware接口回调                       │
├─────────────────────────────────────┤
│  BeanPostProcessor前置处理           │
├─────────────────────────────────────┤
│  @PostConstruct                      │ ← 先执行
├─────────────────────────────────────┤
│  InitializingBean.afterPropertiesSet │ ← 后执行
├─────────────────────────────────────┤
│  BeanPostProcessor后置处理           │
└─────────────────────────────────────┘

销毁时机

Java
┌─────────────────────────────────────┐
│  容器关闭                            │
├─────────────────────────────────────┤
│  @PreDestroy                         │ ← 先执行
├─────────────────────────────────────┤
│  DisposableBean.destroy              │ ← 后执行
├─────────────────────────────────────┤
│  自定义destroy-method                │
└─────────────────────────────────────┘

实现示例

XML
@Component
public class DatabaseConnection implements InitializingBean, DisposableBean {

    private Connection connection;
    private String url;
    private String username;

    @Override
    public void afterPropertiesSet() throws Exception {
        // 属性注入完成后初始化
        connection = DriverManager.getConnection(url, username, password);
        System.out.println("数据库连接初始化完成");
    }

    @Override
    public void destroy() throws Exception {
        // Bean销毁时清理
        if (connection != null && !connection.isClosed()) {
            connection.close();
            System.out.println("数据库连接已关闭");
        }
    }
}

与注解方式对比

Java
@Component
public class LifecycleBean implements InitializingBean, DisposableBean {

    @PostConstruct  // 先于afterPropertiesSet
    public void initAnnotation() {
        System.out.println("@PostConstruct执行");
    }

    @Override
    public void afterPropertiesSet() {
        System.out.println("afterPropertiesSet执行");
    }

    @PreDestroy  // 先于destroy
    public void destroyAnnotation() {
        System.out.println("@PreDestroy执行");
    }

    @Override
    public void destroy() {
        System.out.println("destroy执行");
    }
}

// 执行顺序:
// 初始化: @PostConstruct → afterPropertiesSet
// 销毁: @PreDestroy → destroy
方式执行顺序特点
@PostConstruct第一JSR-250标准,推荐使用
InitializingBean第二Spring接口,耦合容器
@PreDestroy第一JSR-250标准,推荐使用
DisposableBean第二Spring接口,耦合容器

推荐使用注解方式,减少对Spring接口的依赖。

XML配置init-method/destroy-method

Java
<bean id="myBean" class="com.example.MyBean"
      init-method="customInit"
      destroy-method="customDestroy"/>
Java
public class MyBean {
    public void customInit() {
        System.out.println("自定义初始化方法");
    }

    public void customDestroy() {
        System.out.println("自定义销毁方法");
    }
}

// 执行顺序:
// 初始化: @PostConstruct → afterPropertiesSet → customInit
// 销毁: @PreDestroy → destroy → customDestroy

三种方式组合执行顺序

text
初始化顺序:
1. @PostConstruct
2. InitializingBean.afterPropertiesSet
3. XML/init-method

销毁顺序:
1. @PreDestroy
2. DisposableBean.destroy
3. XML/destroy-method

实际应用场景

缓存初始化

text
@Component
public class CacheManager implements InitializingBean, DisposableBean {

    private Map<String, Object> cache;
    private ScheduledExecutorService scheduler;

    @Override
    public void afterPropertiesSet() {
        cache = new ConcurrentHashMap<>();
        scheduler = Executors.newScheduledThreadPool(1);
        // 启动定时清理任务
        scheduler.scheduleAtFixedRate(this::evictExpired, 1, 1, TimeUnit.HOURS);
    }

    @Override
    public void destroy() {
        scheduler.shutdown();
        cache.clear();
    }

    private void evictExpired() {
        // 清理过期缓存
    }
}

连接池管理

text
@Component
public class ConnectionPool implements InitializingBean, DisposableBean {

    private List<Connection> connections;
    private int poolSize = 10;

    @Override
    public void afterPropertiesSet() throws Exception {
        connections = new ArrayList<>(poolSize);
        for (int i = 0; i < poolSize; i++) {
            connections.add(createConnection());
        }
    }

    @Override
    public void destroy() throws Exception {
        for (Connection conn : connections) {
            conn.close();
        }
        connections.clear();
    }
}

要点总结

  • InitializingBean在属性注入后、@PostConstruct后执行
  • DisposableBean在@PreDestroy后执行
  • @PostConstruct/@PreDestroy优先于接口方法
  • 推荐使用注解,减少Spring接口耦合
  • 三种方式可组合使用,按固定顺序执行

📝 发现内容有误?点击此处直接编辑

← 上一篇 FactoryBean
下一篇 → SmartInitializingSingleton
想查看更多题目和详细解析?
小程序提供完整的题库、模拟考试和详细解析
马上就来

长按或扫描二维码,立即体验

扫码体验小程序
马上就来
使用微信扫描二维码
立即体验完整题库