高仿真的类-ApplicationContext
生活随笔
收集整理的這篇文章主要介紹了
高仿真的类-ApplicationContext
小編覺得挺不錯的,現在分享給大家,幫大家做個參考.
/*** 按之前源碼分析的套路,IOC、DI、MVC、AOP*/
public class V1ApplicationContext extends V1DefaultListableBeanFactory implements V1BeanFactory {private String [] configLoactions;private V1BeanDefinitionReader reader;//單例的IOC容器緩存private Map<String,Object> singletonObjects = new ConcurrentHashMap<String, Object>();//通用的IOC容器private Map<String,V1BeanWrapper> factoryBeanInstanceCache = new ConcurrentHashMap<String, V1BeanWrapper>();public V1ApplicationContext(String... configLoactions){this.configLoactions = configLoactions;try {refresh();} catch (Exception e) {e.printStackTrace();}}@Overridepublic void refresh() throws Exception{//1、定位,定位配置文件reader = new V1BeanDefinitionReader(this.configLoactions);//2、加載配置文件,掃描相關的類,把它們封裝成BeanDefinitionList<V1BeanDefinition> beanDefinitions = reader.loadBeanDefinitions();//3、注冊,把配置信息放到容器里面(偽IOC容器)doRegisterBeanDefinition(beanDefinitions);//4、把不是延時加載的類,有提前初始化doAutowrited();}//只處理非延時加載的情況private void doAutowrited() {for (Map.Entry<String, V1BeanDefinition> beanDefinitionEntry : super.beanDefinitionMap.entrySet()) {String beanName = beanDefinitionEntry.getKey();if(!beanDefinitionEntry.getValue().isLazyInit()) {try {getBean(beanName);} catch (Exception e) {e.printStackTrace();}}}}private void doRegisterBeanDefinition(List<V1BeanDefinition> beanDefinitions) throws Exception {for (V1BeanDefinition beanDefinition: beanDefinitions) {if(super.beanDefinitionMap.containsKey(beanDefinition.getFactoryBeanName())){throw new Exception("The “" + beanDefinition.getFactoryBeanName() + "” is exists!!");}super.beanDefinitionMap.put(beanDefinition.getFactoryBeanName(),beanDefinition);}//到這里為止,容器初始化完畢}public Object getBean(Class<?> beanClass) throws Exception {return getBean(beanClass.getName());}//依賴注入,從這里開始,通過讀取BeanDefinition中的信息//然后,通過反射機制創建一個實例并返回//Spring做法是,不會把最原始的對象放出去,會用一個BeanWrapper來進行一次包裝//裝飾器模式://1、保留原來的OOP關系//2、我需要對它進行擴展,增強(為了以后AOP打基礎)public Object getBean(String beanName) throws Exception {V1BeanDefinition V1BeanDefinition = this.beanDefinitionMap.get(beanName);Object instance = null;//這個邏輯還不嚴謹,自己可以去參考Spring源碼//工廠模式 + 策略模式V1BeanPostProcessor postProcessor = new V1BeanPostProcessor();postProcessor.postProcessBeforeInitialization(instance,beanName);instance = instantiateBean(beanName,V1BeanDefinition);//3、把這個對象封裝到BeanWrapper中V1BeanWrapper beanWrapper = new V1BeanWrapper(instance);//singletonObjects//factoryBeanInstanceCache//4、把BeanWrapper存到IOC容器里面
// //1、初始化// //class A{ B b;}
// //class B{ A a;}
// //先有雞還是先有蛋的問題,一個方法是搞不定的,要分兩次//2、拿到BeanWraoper之后,把BeanWrapper保存到IOC容器中去this.factoryBeanInstanceCache.put(beanName,beanWrapper);postProcessor.postProcessAfterInitialization(instance,beanName);// //3、注入populateBean(beanName,new V1BeanDefinition(),beanWrapper);return this.factoryBeanInstanceCache.get(beanName).getWrappedInstance();}private void populateBean(String beanName, V1BeanDefinition V1BeanDefinition, V1BeanWrapper V1BeanWrapper) {Object instance = V1BeanWrapper.getWrappedInstance();// V1BeanDefinition.getBeanClassName();Class<?> clazz = V1BeanWrapper.getWrappedClass();//判斷只有加了注解的類,才執行依賴注入if(!(clazz.isAnnotationPresent(V1Controller.class) || clazz.isAnnotationPresent(V1Service.class))){return;}//獲得所有的fieldsField[] fields = clazz.getDeclaredFields();for (Field field : fields) {if(!field.isAnnotationPresent(V1Autowired.class)){ continue;}V1Autowired autowired = field.getAnnotation(V1Autowired.class);String autowiredBeanName = autowired.value().trim();if("".equals(autowiredBeanName)){autowiredBeanName = field.getType().getName();}//強制訪問field.setAccessible(true);try {//為什么會為NULL,先留個坑if(this.factoryBeanInstanceCache.get(autowiredBeanName) == null){ continue; }
// if(instance == null){
// continue;
// }field.set(instance,this.factoryBeanInstanceCache.get(autowiredBeanName).getWrappedInstance());} catch (IllegalAccessException e) {e.printStackTrace();}}}private Object instantiateBean(String beanName, V1BeanDefinition V1BeanDefinition) {//1、拿到要實例化的對象的類名String className = V1BeanDefinition.getBeanClassName();//2、反射實例化,得到一個對象Object instance = null;try {
// V1BeanDefinition.getFactoryBeanName()//假設默認就是單例,細節暫且不考慮,先把主線拉通if(this.singletonObjects.containsKey(className)){instance = this.singletonObjects.get(className);}else {Class<?> clazz = Class.forName(className);instance = clazz.newInstance();this.singletonObjects.put(className,instance);this.singletonObjects.put(V1BeanDefinition.getFactoryBeanName(),instance);}}catch (Exception e){e.printStackTrace();}return instance;}public String[] getBeanDefinitionNames() {return this.beanDefinitionMap.keySet().toArray(new String[this.beanDefinitionMap.size()]);}public int getBeanDefinitionCount(){return this.beanDefinitionMap.size();}public Properties getConfig(){return this.reader.getConfig();}
}
?
總結
以上是生活随笔為你收集整理的高仿真的类-ApplicationContext的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 高仿真的类-DefaultListabl
- 下一篇: 高仿真的类-BeanDefinition