@PostConstruct
和@PreDestroy
是两个作用于Servlet生命周期的注解,相信从 Servlet 开始学 Java 后台开发的同学对他应该不陌生。
被这两个注解修饰的方法可以保证在整个 Servlet 生命周期只被执行一次,即使 Web 容器在其内部中多次实例化该方法所在的 bean。
这两个注解分别有什么作用呢?
@PostConstruct
: 用来修饰方法,标记在项目启动的时候执行这个方法,一般用来执行某些初始化操作比如全局配置。PostConstruct
注解的方法会在构造函数之后执行,Servlet 的init()
方法之前执行。@PreDestroy
: 当 bean 被 Web 容器的时候被调用,一般用来释放 bean 所持有的资源。。PostConstruct
注解的方法会在Servlet 的destroy()
方法之前执行。被这个注解修饰的方法需要满足下面这些基本条件:
我们新建一个 Spring 程序,其中有一段代码是这样的,输出结果会是什么呢?
import org.springframework.context.annotation.Configuration;
import javax.annotation.PostConstruct;
import javax.annotation.PreDestroy;
@Configuration
public class MyConfiguration {
public MyConfiguration() {
System.out.println("构造方法被调用");
}
@PostConstruct
private void init() {
System.out.println("PostConstruct注解方法被调用");
}
@PreDestroy
private void shutdown() {
System.out.println("PreDestroy注解方法被调用");
}
}
输出结果如下:
但是 J2EE已在Java 9中弃用 @PostConstruct
和@PreDestroy
这两个注解 ,并计划在Java 11中将其删除。我们有什么更好的替代方法吗?当然有!而且,我比较推荐使用这种方式。
package cn.javaguide.config;
import org.springframework.beans.factory.DisposableBean;
import org.springframework.beans.factory.InitializingBean;
import org.springframework.context.annotation.Configuration;
@Configuration
public class MyConfiguration2 implements InitializingBean, DisposableBean {
public MyConfiguration2() {
System.out.println("构造方法被调用");
}
@Override
public void afterPropertiesSet() {
System.out.println("afterPropertiesSet方法被调用");
}
@Override
public void destroy() {
System.out.println("destroy方法被调用");
}
}
输出结果如下,可以看出实现Spring 提供的 InitializingBean
和 DisposableBean
接口的效果和使用@PostConstruct
和@PreDestroy
注解的效果一样。
如果你还是非要使用 Java 9 及以后的版本使用 @PostConstruct
和@PreDestroy
这两个注解的话,你也可以手动添加相关依赖。
Maven:
<dependency>
<groupId>javax.annotation</groupId>
<artifactId>javax.annotation-api</artifactId>
<version>1.3.2</version>
</dependency>
Gradle:
compile group: 'javax.annotation', name: 'javax.annotation-api', version: '1.3.2'
“源码地址:https://github.com/Snailclimb/springboot-guide/tree/master/source-code/basis/life-cycle-annotation”