This is the 9th day of my participation in the August Wen Challenge.More challenges in August

directory

The scope of the Bean

1. Single-instance Bean declarations

2. Multi-instance Bean declarations

Second, the Bean’s life cycle

1. Bean initialization and destruction

2. Bean backend processor

Hello, I’m Grey Ape! A super bug writing program ape!

When using Spring for IOC configuration, the configuration and use of beans has always been an important part. Meanwhile, how to use and create bean objects reasonably is also a part that friends need to pay attention to when learning and using Spring. So in this article I’m going to tell you about the scope and life cycle of beans in Spring.

The scope of the Bean

First let’s talk about the scope of beans.

** Typically, the configuration information we write in the IOC container is created when our IOC container is running. ** This causes us to fetch single-instance bean objects from the IOC container.

This means that no matter how many getBean() methods we use, the same JavaBean we get is the same object, a singleton Bean, which is shared by the entire project.

** In Spring, you can set the scope of a bean in the scope property of an element to determine whether the bean is singleton or multi-instance. ** The Scope attribute has four parameters, which can be used as follows:

1. Single-instance Bean declarations

** By default, Spring creates only one instance for each bean declared in the IOC container, which can be shared across the entire IOC container: all subsequent getBean() calls and bean references will return this unique bean instance. This scope is called a Singleton, and ** it is the default scope for all beans. That’s a single instance.

To verify this statement, we create a single-instance bean in IOC and get the bean object for comparison:

<! <bean id="book02" class=" com.spring.beans.book "scope="singleton"></bean>Copy the code

Test whether the obtained singleton bean is the same:

Book book03 = (Book)iocContext3.getBean("book02"); Book book04 = (Book)iocContext3.getBean("book02"); System.out.println(book03==book04); }Copy the code

The result is true;

2. Multi-instance Bean declarations

And if there are single instances, there must be multiple instances. We can set the prototype parameter to the scope property of the bean object to indicate that the instance is multi-instance, fetch the multi-instance beans from the IOC container, and compare the obtained multi-instance beans.

<! Prototype Multiinstance bean () : not created when the container is created Class =" com.spring.beans.book "scope="prototype"></bean>Copy the code

Test whether the obtained multi-instance bean is the same:

Book book01 = (Book)iocContext3.getBean("book01"); Book book02 = (Book)iocContext3.getBean("book01"); System.out.println(book01==book02); }Copy the code

The result is false

This shows that bean objects created through multiple instances are different.

Note here:

There is also a difference between single-instance and multi-instance bean creation. When the bean is scoped as a singleton, Spring creates the object instance of the bean when the IOC container object is created. When the bean is scoped to prototype, the IOC container creates the instance object of the bean when it gets the instance of the bean.

Second, the Bean’s life cycle

1. Bean initialization and destruction

In fact, every bean object we create in IOC has a specific life cycle. The bean life cycle can be managed in Spring’s IOC container, and Spring allows specific tasks to be performed at specific points in the bean life cycle. Methods such as those executed when the bean is initialized and those executed when the bean is destroyed.

The Spring IOC container manages the bean lifecycle in six steps:

  1. Create a bean instance through a constructor or factory method
  2. Sets values for bean properties and references to other beans
  3. Call the bean’s initialization method
  4. Beans can be used normally
  5. When the container is closed, the bean’s destruction method is called

What about the declaration of methods that are executed when the bean is initialized and destroyed?

First we should add methods inside the bean class that are executed at initialization and destruction. Such as the following javabean:

package com.spring.beans; public class Book { private String bookName; private String author; /** */ public void myInit() {system.out.println ("book bean created "); Public void myDestory() {system.out.println ("book bean is destroyed "); } public String getBookName() { return bookName; } public void setBookName(String bookName) { this.bookName = bookName; } public String getAuthor() { return author; } public void setAuthor(String author) { this.author = author; } @Override public String toString() { return "Book [bookName=" + bookName + ", author=" + author + "]"; }}Copy the code

When configuring the bean, we can specify initialization and destruction methods for the bean through init-method and destroy-method properties.

<! Destory-method: the method to end the call init-method: <bean id="book01" class=" com.spring.beans.book "destroy-method="myDestory" init-method="myInit"></bean>Copy the code

This way we execute methods when we create and destroy bean objects through the IOC container,

But there is one caveat:

As we said above, the creation times of single-instance beans and multi-instance beans are different, so the execution times of their initial methods and destruction methods are slightly different.

The life cycle of a bean under a single instance

Container start — > Initialization method — > (Container close) destruction method

The life cycle of a bean in multiple instances

Container start — > Call bean — > Initialize method — > Container close (destruction method not executed)

2. Bean backend processor

What is a bean’s post-processor? The bean post-processor allows additional processing of the bean before and after the invocation of the initialization method

The bean post-processor treats all bean instances in the IOC container one by one, rather than a single instance.

Typical applications are to check the correctness of bean properties or to change bean properties based on specific criteria.

The bean backend processor needs to implement the interface:

Org. Springframework. Beans. Factory. Config. BeanPostProcessor.

Before and after the initialization method is called, Spring passes each bean instance to the following two methods of the interface:

PostProcessBeforeInitialization (Object, String) before invoking it

Call after postProcessAfterInitialization (Object, String)

The following is a post-processor implemented in this interface:

package com.spring.beans; import org.springframework.beans.BeansException; import org.springframework.beans.factory.config.BeanPostProcessor; /** * Test the bean's back handler * note that the bean and beanName appear, not arg0, arg1, Need to bind the corresponding source jar package * * / public class MyBeanPostProcessor implements the BeanPostProcessor {/ * * * postProcessBeforeInitialization * Object bean * String beanName Bean name defined in XML container * */ @override public Object postProcessBeforeInitialization(Object bean, String beanName) throws BeansException {// TODO auto-generated method Stub system.out.println (" ["+ BeanName +" beanName+" ); return bean; PostProcessAfterInitialization} / * * * * executed after initialization method * Object String bean * beanName XML containers that are defined in the bean name * * / @ Override public Object postProcessAfterInitialization(Object bean, String beanName) throws BeansException {// TODO auto-generated method Stub system.out.println (" ["+ BeanName +" > < div style = "box-sizing: border-box; ); return bean; }}Copy the code

Add the post-processor to the IOC container:

<! - test the bean's rear processor - > < bean id = "beanPostProcessor" class = "com. Spring. Beans. MyBeanPostProcessor" > < / bean >Copy the code

Since our bean object is now singleton, the container runtime creates the bean object directly and also executes the bean’s post-processor and initialization methods, and then executes the destruction method when the container is destroyed. Our tests are as follows:

/ / * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * bean lifecycle * * * * * * * * * * * * / / because the ApplicationContext is a top-level interface, there is no destroy method close, So you need to use it a child of the interface for receiving ConfigurableApplicationContext iocContext01 = new ClassPathXmlApplicationContext (" ioc1. XML "); @Test public void test01() { iocContext01.getBean("book01"); iocContext01.close(); }Copy the code

Running results:

To summarize the post-processor execution:

  1. Create a bean instance through a constructor or factory method
  2. Sets values for bean properties and references to other beans
  3. Pass the bean instance to rear bean processors * * postProcessBeforeInitialization () * * method
  4. Call the bean’s initialization method
  5. Pass the bean instance to rear bean processors * * postProcessAfterInitialization () * * method
  6. The bean is ready to use
  7. The bean’s destruction method is called when the container is closed

So the life cycle of the bean after adding the bean post-processor is:

Container start — postprocessor before… — > initialization method — > after… — > (container closed) destruction method

This is a tutorial on the scope and life cycle of beans in SpringIOC.

Click “Like” to save it!

I’m grey Ape! See you next time!