主要步骤
- 启动IOC容器后,实例化Bean
- 属性注入
- BeanNameAware 的setBeanName方法
- BeanFactoryAware 的setBeanFactory方法
- ApplicationContextAware的setApplicationContext方法
- BeanPostProcessor的postProcessBeforeInitialization方法
- BeanPostProcessor的前置处理完成后,可以实现postConstruct,InitializingBean的afterPropertiesSet,init-method等方法, 增加我们自定义的逻辑
- BeanPostProcessor的postProcessAfterInitialization方法
- 当Bean不再需要时,会经过清理阶段,如果Bean实现了DisposableBean这个接口,会调用那个其实现的destroy()方法
- 最后,如果这个Bean的Spring配置中配置了destroy-method属性,会自动调用其配置的销毁方法
图
作用域
Spring支持五个作用域,分别是singleton、prototype、request、session、global session
- singleton: 是默认的作用域,在spring IoC容器仅存在一个Bean实例,Bean以单例方式存在,在创建容器时就同时自动创建了一个bean的对象
- prototype: 每次从容器中调用Bean时,都返回一个新的实例,即每次调用getBean()时,相当于执行newXxxBean()。prototype是原型类型,它在我们创建容器的时候并没有实例化,而是当我们获取bean的时候才会去创建一个对象,而且我们每次获取到的对象都不是同一个对象
- request: 每次HTTP请求都会创建一个新的Bean,该作用域仅适用于WebApplicationContext环境
- session: 同一个HTTP Session共享一个Bean,不同Session使用不同的Bean,仅适用于WebApplicationContext环境
- global session: 一般用于Portlet应用环境,该运用域仅适用于WebApplicationContext环境
理解分析
- Bean实现BeanNameAware接口,获取IOC容器中定义的自身bean的ID
- Bean实现BeanFactoryAware接口,获取Bean的工厂
- 实现BeanPostProcessor接口,增加我们自定义的逻辑
- HelloBean
package com.fuzzy.search.controller;
import org.springframework.beans.BeansException;
import org.springframework.beans.factory.BeanFactory;
import org.springframework.beans.factory.BeanFactoryAware;
import org.springframework.beans.factory.BeanNameAware;
import org.springframework.beans.factory.config.BeanPostProcessor;
import org.springframework.stereotype.Component;
/**
* @author yanyugang
* @description 实现BeanNameAware接口,BeanFactoryAware接口
* @date 2019/8/18 21:13
*/
@Component
public class HelloBean implements BeanNameAware, BeanFactoryAware, BeanPostProcessor {
private BeanFactory beanFactory;
// 获取IOC容器中定义的自身bean的ID
@Override
public void setBeanName(String s){
System.out.println("回调setBeanName方法,id属性是" + s);
}
@Override
public void setBeanFactory(BeanFactory beanFactory) throws BeansException{
System.out.println("beanFactory=====>" + beanFactory);
this.beanFactory=beanFactory;
}
// 获取Bean的工厂
public void executeProcess(String beanName){
SayBean sayBean=(SayBean) beanFactory.getBean(beanName);
sayBean.say();
}
// 该方法主要针对spring在bean初始化时调用初始化方法前进行自定义处理
@Override
public Object postProcessBeforeInitialization(Object bean, String beanName) throws BeansException{
// 可以运用 instanceof 对指定的Bean进行自定义处理
System.out.println("BeanPostProcessor的前置处理,beanName====>" + beanName);
return bean;
}
// 该方法主要针对spring在bean初始化时调用初始化方法后进行自定义处理
@Override
public Object postProcessAfterInitialization(Object bean, String beanName) throws BeansException{
System.out.println("BeanPostProcessor的后置处理,beanName====>" + beanName);
return bean;
}
}
- SayBean
package com.fuzzy.search.controller;
import org.springframework.stereotype.Component;
/**
* @author yanyugang
* @description
* @date 2019-08-19 14:41
*/
@Component
public class SayBean {
public void say(){
System.out.printf("Hello World!");
}
}
- FuzzySearchQueryController
package com.fuzzy.search.controller;
import com.fuzzy.search.entity.GridModel;
import org.apache.commons.io.FileUtils;
import org.apache.commons.io.IOUtils;
import org.apache.commons.io.LineIterator;
import org.apache.log4j.Logger;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.ResponseBody;
import org.springframework.web.servlet.ModelAndView;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpSession;
import java.io.File;
import java.io.FileInputStream;
import java.text.DateFormat;
import java.text.SimpleDateFormat;
import java.util.Calendar;
import java.util.Date;
import java.util.Map;
import java.util.concurrent.atomic.AtomicInteger;
@Controller
@RequestMapping("/fuzzySearch")
@SuppressWarnings("all")
public class FuzzySearchQueryController {
private static Logger logger=Logger.getLogger(FuzzySearchQueryController.class);
@Value("${file.path}")
private String filePath;
@Autowired
private HelloBean helloBean;
@RequestMapping("/execute")
public ModelAndView execute(HttpServletRequest request){
ModelAndView view=new ModelAndView("fuzzysearch");
DateFormat sdf=new SimpleDateFormat("yyyy-MM-dd");
Date date=new Date();
Calendar c=Calendar.getInstance();
c.setTime(date);
c.add(Calendar.DAY_OF_MONTH, -3); //当前天数-3
view.addObject("start", sdf.format(c.getTime()));
view.addObject("end", sdf.format(c.getTime()));
view.addObject("timestamp", System.currentTimeMillis());
helloBean.executeProcess("sayBean");
return view;
}
}
- 结果
## IOC容器启动后
回调setBeanName方法,id属性是helloBean
beanFactory=====>org.springframework.beans.factory.support.DefaultListableBeanFactory@3ad420ad: defining beans
## 访问页面,控制台成功打印
Hello World!