Spring Framework 之 Bean的生命周期Lifecycle

在本文中,了解Spring bean的生命周期。我们将学习生命周期阶段,初始化和销毁​​回调方法。我们将学习使用XML配置以及注解配置来控制bean生命周期事件。

目录

1. Bean生命周期
2.生命周期回调方法

1.Bean的生命周期

当容器启动时–需要基于Java或XML bean定义实例化Spring bean。可能还需要执行一些初始化后的步骤,以使其进入可用状态。Spring Boot 应用程序也具有相同的bean生命周期。

之后,当不再需要该bean时,它将被从IoC容器中删除。

Spring bean factory负责管理通过spring容器创建的bean的生命周期。

1.1。生命周期回调

Spring bean factory控制bean的创建和销毁。为了执行一些自定义代码,它提供了回调方法,这些方法可以大致分为两类:

  • 初始化后的回调方法
  • 销毁前回调方法

1.1。图中的生命周期

Spring Bean的生命周期

2.生命周期回调方法

Spring框架提供了以下4种方法来控制 Bean的生命周期事件

  1. InitializingBeanDisposableBean回调接口
  2. *了解特定行为的界面
  3. bean配置文件中的自定义init()destroy()方法
  4. @PostConstruct@PreDestroy注解

2.1。InitializingBean和DisposableBean

容器已在Bean上设置了所有必需的属性之后,org.springframework.beans.factory.InitializingBean接口允许Bean执行初始化工作。

InitializingBean接口指定一个方法:

void afterPropertiesSet() throws Exception;

这不是初始化bean的首选方法,因为它将bean类与spring容器紧密耦合。更好的方法是在文件的bean定义中使用“ init-method ”属性applicationContext.xml

类似地,实现org.springframework.beans.factory.DisposableBean接口允许Bean在包含它的容器被销毁时获得回调。

DisposableBean接口指定一个方法:

void destroy() throws Exception;

A sample bean implementing above interfaces would look like this:


package com.how2codex.task;

import org.springframework.beans.factory.DisposableBean;
import org.springframework.beans.factory.InitializingBean;

public class DemoBean implements InitializingBean, DisposableBean 
{
	//Other bean attributes and methods 
	
	@Override
	public void afterPropertiesSet() throws Exception
	{
		//Bean initialization code
	}
	
	@Override
	public void destroy() throws Exception 
	{
		//Bean destruction code
	}
}

2.2。*了解特定行为的界面

Spring提供了一系列*Aware接口,这些接口允许bean向容器指示它们需要某种基础结构依赖性。每个接口都将要求您实现一种将依赖项注入bean的方法。

这些接口可以概括为:

感知界面 覆盖方法 目的
ApplicationContextAware void setApplicationContext(ApplicationContext applicationContext)抛出BeansException; 希望由其ApplicationContext运行所要通知的任何对象实现的接口。
ApplicationEventPublisherAware void setApplicationEventPublisher(ApplicationEventPublisher applicationEventPublisher); 设置ApplicationEventPublisher运行该对象的位置。
BeanClassLoaderAware void setBeanClassLoader(ClassLoader classLoader); 将bean类加载器提供给bean实例的回调。
BeanFactoryAware void setBeanFactory(BeanFactory beanFactory)抛出BeansException; 将拥有的工厂提供给Bean实例的回调。
BeanNameAware void setBeanName(字符串名称); 在创建此bean的bean工厂中设置bean的名称。
BootstrapContextAware 无效setBootstrapContext(BootstrapContext bootstrapContext); 设置该对象在其中运行的BootstrapContext。
LoadTimeWeaverAware void setLoadTimeWeaver(LoadTimeWeaver loadTimeWeaver); 设置此对象的包含ApplicationContext的LoadTimeWeaver。
MessageSourceAware void setMessageSource(MessageSource messageSource); 设置此对象在其中运行的MessageSource。
NotificationPublisherAware void setNotificationPublisher(NotificationPublisher notificationPublisher); 为当前的托管资源实例设置NotificationPublisher实例。
PortletConfigAware void setPortletConfig(PortletConfig portletConfig); 设置运行该对象的PortletConfig。
PortletContextAware void setPortletContext(PortletContext portletContext); 设置此对象在其中运行的PortletContext。
ResourceLoaderAware void setResourceLoader(ResourceLoader resourceLoader); 设置运行该对象的ResourceLoader。
ServletConfigAware void setServletConfig(ServletConfig servletConfig); 设置运行该对象的ServletConfig。
ServletContextAware void setServletContext(ServletContext servletContext); 设置运行该对象的ServletContext。

Java程序展示了使用感知接口来控制字符串bean生命周期的用法。

package com.how2codex.task;

import org.springframework.beans.BeansException;
import org.springframework.beans.factory.BeanClassLoaderAware;
import org.springframework.beans.factory.BeanFactory;
import org.springframework.beans.factory.BeanFactoryAware;
import org.springframework.beans.factory.BeanNameAware;
import org.springframework.context.ApplicationContext;
import org.springframework.context.ApplicationContextAware;
import org.springframework.context.ApplicationEventPublisher;
import org.springframework.context.ApplicationEventPublisherAware;
import org.springframework.context.MessageSource;
import org.springframework.context.MessageSourceAware;
import org.springframework.context.ResourceLoaderAware;
import org.springframework.context.weaving.LoadTimeWeaverAware;
import org.springframework.core.io.ResourceLoader;
import org.springframework.instrument.classloading.LoadTimeWeaver;
import org.springframework.jmx.export.notification.NotificationPublisher;
import org.springframework.jmx.export.notification.NotificationPublisherAware;

public class DemoBean implements ApplicationContextAware,
		ApplicationEventPublisherAware, BeanClassLoaderAware, BeanFactoryAware,
		BeanNameAware, LoadTimeWeaverAware, MessageSourceAware,
		NotificationPublisherAware, ResourceLoaderAware
{
	@Override
	public void setResourceLoader(ResourceLoader arg0) {
		// TODO Auto-generated method stub
	}

	@Override
	public void setNotificationPublisher(NotificationPublisher arg0) {
		// TODO Auto-generated method stub

	}

	@Override
	public void setMessageSource(MessageSource arg0) {
		// TODO Auto-generated method stub
	}

	@Override
	public void setLoadTimeWeaver(LoadTimeWeaver arg0) {
		// TODO Auto-generated method stub
	}

	@Override
	public void setBeanName(String arg0) {
		// TODO Auto-generated method stub
	}

	@Override
	public void setBeanFactory(BeanFactory arg0) throws BeansException {
		// TODO Auto-generated method stub
	}

	@Override
	public void setBeanClassLoader(ClassLoader arg0) {
		// TODO Auto-generated method stub
	}

	@Override
	public void setApplicationEventPublisher(ApplicationEventPublisher arg0) {
		// TODO Auto-generated method stub
	}

	@Override
	public void setApplicationContext(ApplicationContext arg0)
			throws BeansException {
		// TODO Auto-generated method stub
	}
}

2.3。自定义init()和destroy()方法

可以通过两种方式定义bean配置文件中的default initdestroymethod:

  • 适用于单个bean的bean 本地定义
  • 全局定义适用于在bean上下文中定义的所有bean
2.3.1。Bean本地定义

本地定义如下。

<beans>

	<bean id="demoBean" class="com.how2codex.task.DemoBean" 
					init-method="customInit" 
					destroy-method="customDestroy"></bean>

</beans>
2.3.2。全局定义

全局定义如下。这些方法将为<beans>标记下给出的所有bean定义调用。当您有一种定义通用方法名称的模式时,例如init()destroy()对于所有bean 来说,它们都是一致的,它们很有用。此功能可帮助您不为所有bean单独提及init和destroy方法名称。

<beans default-init-method="customInit" default-destroy-method="customDestroy">   

    	<bean id="demoBean" class="com.how2codex.task.DemoBean"></bean>

</beans>

显示在bean XML配置文件中配置的方法的Java程序。

package com.how2codex.task;

public class DemoBean 
{
	public void customInit() 
	{
		System.out.println("Method customInit() invoked...");
	}

	public void customDestroy() 
	{
		System.out.println("Method customDestroy() invoked...");
	}
}

2.4。@PostConstruct和@PreDestroy

从Spring 2.5开始,您还可以使用注解来指定使用@PostConstruct@PreDestroy注解的生命周期方法。

  • @PostConstruct 带注解的方法将在使用默认构造函数构造了bean之后,并且在实例返回给请求对象之前被调用。
  • @PreDestroy 即将在Bean容器中销毁Bean之前调用带注解的方法。

Java程序,以显示注解配置的用法来控制使用注解。

package com.how2codex.task;

import javax.annotation.PostConstruct;
import javax.annotation.PreDestroy;

public class DemoBean 
{
	@PostConstruct
	public void customInit() 
	{
		System.out.println("Method customInit() invoked...");
	}
	
	@PreDestroy
	public void customDestroy() 
	{
		System.out.println("Method customDestroy() invoked...");
	}
}

因此,这一切都与Spring容器内部的Spring bean生命周期有关。记住给定的生命周期事件类型,这是Spring面试中经常问到的问题

学习愉快!

saigon has written 1440 articles

Leave a Reply