`
xiang37
  • 浏览: 433164 次
  • 性别: Icon_minigender_1
  • 来自: 南京
社区版块
存档分类
最新评论

Spring源码学习之二

阅读更多

本次主要记录一下spring中的依赖注入。

 

先来段代码,

package com.xiva.mySpring;

import java.lang.reflect.Constructor;
import java.lang.reflect.Method;
import java.net.URL;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

import org.dom4j.Document;
import org.dom4j.Element;
import org.dom4j.XPath;
import org.dom4j.io.SAXReader;

import com.xiva.bean.MyBean;
import com.xiva.bean.PropertyDefinition;

/**
 * 
 * @author XIVA
 * @Description 简化的Spring容器
 */
public class XivaContext extends XivaAbsAppContext{

	private List<MyBean> beanList = new ArrayList<MyBean>();
	
	private Map<String, Object> sigletons = new HashMap<String, Object>();
	
	private Map<String, PropertyDefinition> property = new HashMap<String, PropertyDefinition>();
	
	
	public XivaContext(String xmlPath){
		this.readXML(xmlPath);
		this.instanceBean();
		this.injectBean();
	}
	
	private void injectBean() {
		// TODO Auto-generated method stub
		for(Map.Entry<String, PropertyDefinition> map :property.entrySet()){
			String key = map.getKey();
			PropertyDefinition value = map.getValue();
			
			Object object = sigletons.get(key);
			Object injectObject  = sigletons.get(value.getRef());
			Class<?> clazz = object.getClass();
			try{
				String methodName = "set" + firToUpper(value.getRef());
				Method setMethod = clazz.getMethod(methodName, injectObject.getClass().getInterfaces());
				setMethod.invoke(object, injectObject);
			}catch(Exception e){
				e.printStackTrace();
			}
		}
		
	}

	/**
	 * @Description 解析spring配置文件,初始化bean;其中对bean中配置的property
	 * @author XIVA
	 * @param fileName
	 */
	@SuppressWarnings("unchecked")
	private void readXML(String fileName){
		SAXReader saxReader = new SAXReader();
		Document document = null;
		try{
			URL xmlPath = this.getClass().getClassLoader().getResource(fileName);
			document = saxReader.read(xmlPath);
			Map<String, String> nsMap = new HashMap<String, String>();
			nsMap.put("ns", "http://www.springframework.org/schema/beans");//加入命名空间
			XPath xsub = document.createXPath("//ns:beans/ns:bean");//
			xsub.setNamespaceURIs(nsMap);//设置命名空间
			List<Element> beans = xsub.selectNodes(document);//获取节点
			MyBean bean = null;
			for (Element element:beans){
				String id = element.attributeValue("id");
				String clazz = element.attributeValue("class");
				if (id!=null && clazz!=null){
					bean = new MyBean(id, clazz);
					beanList.add(bean);
				}
				List<Element> pList = element.elements("property");
				if (pList != null && pList.size() > 0){
					PropertyDefinition propDef = null;
					for (Element pEle:pList){
						String name = pEle.attributeValue("name");
						String ref = pEle.attributeValue("ref");
						if (name!=null && ref!=null){
							propDef = new PropertyDefinition(name,ref);
							property.put(id, propDef);
						}
					}
				}
			}
		}catch(Exception e){
			e.printStackTrace();
		}
	}
	
	/**
	 * 
	 * @Description 实例化bean
	 * @author XIVA
	 */
	private void instanceBean(){
		Object object = null;
		for(MyBean bean:beanList){
			try{
				String clazzStr = bean.getBeanClass();
				Class<?> clazz = Class.forName(clazzStr);
				for(Constructor<?> con:clazz.getDeclaredConstructors()){
					con.setAccessible(true);
				}
				object = clazz.newInstance();
				sigletons.put(bean.getBeanId(), object);
			}catch(Exception e){
				e.printStackTrace();
			}
		}
	}
	
	/**
	 * 获取Bean实例
	 */
	@Override
	public Object getBean(String beanName) {
		// TODO Auto-generated method stub
		return sigletons.get(beanName);
	}
	
	/**
	 * 首字母大写
	 * @param field
	 * @return
	 */
	private static String firToUpper(String field){
		
		String firStr = field.substring(0, 1);
		firStr = firStr.toUpperCase();
		field = firStr + field.substring(1, field.length());
		return field;
	}

}

 依赖注入,对于Spring的实现有两种;第一种是在构造函数中,来注入外部的类的实例,第二种方式是通过set方法来实例化。当然有了JPA后了,我们又可以通过注解autoware来实现,但是这种原理都是一样的。都是通过类反射,然后找到相应的注解或者解析xml来实现。

	/**
	 * 
	 * @Description 注入
	 * @author XIVA
	 */
	private void injectBean() {
		// TODO Auto-generated method stub
		for (Map.Entry<String, PropertyDefinition> map :property.entrySet()){
			String key = map.getKey();
			PropertyDefinition value = map.getValue();
			
			Object object = sigletons.get(key);
			Object injectObject  = sigletons.get(value.getRef());
			Class<?> clazz = object.getClass();
			try{
				String methodName = "set" + firToUpper(value.getRef());
				Method setMethod = clazz.getMethod(methodName, injectObject.getClass().getInterfaces());
				setMethod.invoke(object, injectObject);
			}catch (Exception e){
				e.printStackTrace();
			}
		}	
	}

 上面方法就是通过反射来注入bean的。

 

List<Element> pList = element.elements("property");
				if (pList != null && pList.size() > 0){
					PropertyDefinition propDef = null;
					for (Element pEle:pList){
						String name = pEle.attributeValue("name");
						String ref = pEle.attributeValue("ref");
						if (name!=null && ref!=null){
							propDef = new PropertyDefinition(name,ref);
							property.put(id, propDef);
						}
					}
				}
 

这段代码是解析xml文件中property属性来放入

private Map<String, PropertyDefinition> property = new HashMap<String, PropertyDefinition>();

上面定义的map中。
<bean id="moduleService" class="com.xiva.module.service.impl.ModuleServiceImpl">
			<property name="moduleDao" ref="moduleDao"></property>
		</bean>
 上面的property就是注入。
分享到:
评论

相关推荐

    Spring学习笔记&源码

    本资料“Spring学习笔记&源码”是基于网易云课堂黑马程序员的Spring四天精通课程,旨在帮助学习者深入理解和实践Spring框架。 笔记部分可能会涵盖以下内容: 1. **Spring概述**:介绍Spring框架的历史、特点和主要...

    spring源码学习之思维导图

    1、spring 的整体架构 2、spring的基本实现(xml的加载原理、标签解析、bean加载) 3、容器扩展 4、ioc和aop 5、事务 6、springmvc 7、dispatcherServlet

    Spring源码学习加注释,方便学习.zip

    spring源码中文注释方便学习,spring源码学习加注释。 spring源码中文注释方便学习,spring源码学习加注释。 spring源码中文注释方便学习,spring源码学习加注释。 spring源码中文...

    Spring高级源码学习笔记.zip

    总之,Spring源码学习是一个深化编程技能,理解设计模式,以及提高问题解决能力的过程。通过深入研究,程序员不仅可以优化自己的代码,还能更高效地利用Spring框架提供的功能,提升项目的可维护性和扩展性。

    spring 源码中文注释

    Spring框架是Java开发中最广泛应用的轻量级框架之一,它以IoC(Inversion of Control,控制反转)和AOP...通过学习源码,我们可以更全面地掌握Spring框架,提升自己的技术水平,更好地应对各种复杂的软件开发挑战。

    spring 源码环境搭建

    "spring源码" 是指 Spring 框架的源代码。 部分内容解释 1. 下载 GitHub 客户端安装 下载 GitHub 客户端是因为 Spring 源码托管在 GitHub 上,所以我们需要下载 GitHub 客户端来 clone Spring 源码。安装成功后,...

    spring源码注释中文

    Spring 源码注释中文版的提供,使得开发者能够更加深入地理解 Spring 的工作原理,无需经过复杂的编译过程,可以直接阅读源码注释来学习。 Spring 框架主要由以下几个关键模块组成: 1. **Core Container(核心...

    构建为eclipse项目的spring源码

    在Eclipse中构建Spring源码项目,可以帮助我们深入理解Spring的工作原理,从而更好地利用它来构建高效、可维护的Java应用。以下将详细阐述如何构建和探索Spring源码。 1. **获取源码** Spring源码可以从官方GitHub...

    spring源码

    学习Spring源码有助于深入理解其内部工作原理,例如bean的生命周期管理、AOP的实现、以及MVC的请求处理流程。这将有助于开发者更高效地利用Spring框架,编写出高质量、高性能的Java应用。通过分析源码,开发者还可以...

    spring源码分析专题学习资源

    spring源码分析专题,源码分析视频,对spring的源码进行分析

    spring源码(注释+测试版)

    这份"spring源码(注释+测试版)"提供了Spring框架的源代码,带有注释和测试用例,对于开发者深入理解Spring的工作原理非常有帮助。 1. **spring-core**:这是Spring框架的基础模块,包含了核心的工具类和资源处理...

    Spring源码学习一:源码分析概述1

    Spring源码学习概述 Spring是Java生态系统中的一种流行的开源框架,由Rod Johnson创立于2003年。Spring框架的主要目标是使Java应用程序的开发变得更加简洁、灵活和可维护。Spring框架的核心思想是基于依赖注入...

    spring框架学习源码

    Spring框架是Java开发中最常用的轻量级开源框架之一,它为开发者提供了全面的控制反转(IoC)和面向切面编程(AOP)功能。SpringCloud则是基于Spring Boot构建的一套微服务解决方案,用于简化分布式系统开发。在这个...

    Spring Boot学习之Shiro源码

    Spring Boot学习之Shiro源码【学习狂神说,自己手动书写,可以实现正常所需的功能】 Spring Boot学习之Shiro源码【学习狂神说,自己手动书写,可以实现正常所需的功能】 Spring Boot学习之Shiro源码【学习狂神说,...

    Spring5 源码分析(第 2 版)-某Tom老师

    Spring作为Java领域最为广泛应用的框架之一,其源码的深入理解对于开发者来说至关重要。这篇文档通过详细剖析Spring5的源码,将复杂的概念以深入浅出的方式呈现出来,让学习者能够更好地掌握Spring的内在工作原理。 ...

    深入剖析Spring Web源码 pdf高清版(第二版)

    3. 设计模式学习:Spring源码中包含了许多经典的设计模式,如工厂模式、代理模式、装饰者模式等,学习源码有助于提升设计能力。 综上所述,《深入剖析Spring Web源码》(第二版) 对于想要深入理解和优化Spring Web...

    Spring攻略(第二版)书籍源码

    《Spring攻略(第二版)书籍源码》是一个深入学习Spring框架的重要资源,它包含了作者在编写书籍过程中所使用的完整代码示例。这份源码旨在帮助读者更好地理解和实践Spring框架的各种功能和最佳实践。 Spring框架是...

    Tom_深入分析Spring源码

    《Spring源码分析》这份资料深入探讨了Spring框架的核心机制,尤其聚焦于Spring5版本。Spring作为Java领域中最重要的轻量级应用框架之一,它的设计理念、实现方式以及工作原理对于任何想成为优秀Java开发者的人都至...

    idea+gradle构建spring源码环境.docx

    在本文中,我们将详细介绍如何使用 IDEA 和 Gradle 构建 Spring 源码环境,以便深入学习 Spring 源码。下面是具体的步骤和知识点总结。 一、下载 Spring 源码 下载 Spring 源码有两种方式:一种是直接下载 zip ...

Global site tag (gtag.js) - Google Analytics