您的位置:首页 > 编程语言 > Java开发

手写springIoc框架

2020-01-13 00:00 183 查看

springIoc的底层实现原理

1.读取bean的XML配置文件

2.使用beanId查找bean配置,并获取配置文件中class地址。

3.使用Java反射技术实例化对象

4.获取属性配置,使用反射技术进行赋值

使用人家spring框架读取对象

创建实体

[code]
package com.itmayiedu.service;

public class UserEntity {
private String userId;
private String userName;

public UserEntity(){
System.out.println("无参构造函数....");
}

public String getUserId() {

return userId;
}

public void setUserId(String userId) {

this.userId = userId;
}

public String getUserName() {

return userName;
}

public void setUserName(String userName) {

this.userName = userName;
}

}

创建spring的配置文件 application.xml

[code]<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:aop="http://www.springframework.org/schema/aop"
xmlns:tx="http://www.springframework.org/schema/tx" xmlns:context="http://www.springframework.org/schema/context"
xsi:schemaLocation="
http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans-3.0.xsd
http://www.springframework.org/schema/tx
http://www.springframework.org/schema/tx/spring-tx-3.0.xsd
http://www.springframework.org/schema/aop
http://www.springframework.org/schema/aop/spring-aop-3.0.xsd
http://www.springframework.org/schema/context
http://www.springframework.org/schema/context/spring-context-3.0.xsd">

<bean id="user1" class="com.itmayiedu.service.UserEntity">
<property name="userId" value="0002"></property>
<property name="userName" value="张三"></property>
</bean>
<bean id="user2" class="com.itmayiedu.service.UserEntity">
<property name="userId" value="0002"></property>
<property name="userName" value="张三"></property>
</bean>
</beans>

读取配置文件

[code]package com.itmayiedu.service;

import org.springframework.context.support.ClassPathXmlApplicationContext;

@SuppressWarnings("resource")
public class Main {

public static void main(String[] args) {
//1.读取springxml配置
ClassPathXmlApplicationContext classPathXmlApplicationContext = new ClassPathXmlApplicationContext(
"applicationContext.xml");
//2.获取bean对象
UserEntity userEntity = (UserEntity) classPathXmlApplicationContext.getBean("user1");
System.out.println(userEntity.getUserId()+"----"+userEntity.getUserName());
}

}

自己手写springIoc框架

编写配置文件user.xml

[code]<?xml version="1.0" encoding="UTF-8"?>
<beans>
<bean id="user1" class="com.itmayiedu.entity.UserEntity">
<property name="userId" value="0001"></property>
<property name="userName" value="张三"></property>
</bean>
<bean id="user2" class="com.itmayiedu.entity.UserEntity">
<property name="userId" value="0002"></property>
<property name="userName" value="张三"></property>
</bean>
</beans>

编写读取user.xml的方法

[code]
package com.itmayiedu.classFrorm;

import java.lang.reflect.Field;
import java.util.List;

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

import com.itmayiedu.entity.UserEntity;

public class ClassPathXmlApplicationContext {
private String xmlPath;

public ClassPathXmlApplicationContext(String xmlPath) {
this.xmlPath = xmlPath;
}

public Object getBean(String beanId) throws DocumentException, ClassNotFoundException, NoSuchFieldException,
SecurityException, IllegalArgumentException, IllegalAccessException, InstantiationException {
// spring 加载过程 或者spring ioc实现原理
// 1.读取xml配置文件
// 获取xml解析器
SAXReader saxReader = new SAXReader();
// this.getClass().getClassLoader().getResourceAsStream("xmlPath")
// 获取当前项目路径
Document read = saxReader.read(this.getClass().getClassLoader().getResourceAsStream(xmlPath));
// 获取跟节点对象
Element rootElement = read.getRootElement();
List<Element> elements = rootElement.elements();
Object obj = null;
for (Element sonEle : elements) {
// 2.获取到每个bean配置 获取class地址
String sonBeanId = sonEle.attributeValue("id");
if (!beanId.equals(sonBeanId)) {
continue;
}
String beanClassPath = sonEle.attributeValue("class");
// 3.拿到class地址 进行反射实例化对象 ,使用反射api 为私有属性赋值
Class<?> forName = Class.forName(beanClassPath);
obj = forName.newInstance();
// 拿到成员属性
List<Element> sonSoneleme = sonEle.elements();
for (Element element : sonSoneleme) {
String name = element.attributeValue("name");
String value = element.attributeValue("value");
// 使用反射api 为私有属性赋值
Field declaredField = forName.getDeclaredField(name);
//运行往私有成员赋值
declaredField.setAccessible(true);
declaredField.set(obj, value);
}

}
// 3.拿到class地址 进行反射实例化对象 ,使用反射api 为私有属性赋值
return obj;
}

public static void main(String[] args) throws ClassNotFoundException, NoSuchFieldException, SecurityException,
IllegalArgumentException, IllegalAccessException, InstantiationException, DocumentException {
ClassPathXmlApplicationContext appLication = new ClassPathXmlApplicationContext("user.xml");
Object bean = appLication.getBean("user1");
UserEntity user = (UserEntity) bean;
System.out.println(user.getUserId() + "----" + user.getUserName());
}

}

创建对应的user实体省略了

  • 点赞
  • 收藏
  • 分享
  • 文章举报
笨笨猪Insist 发布了31 篇原创文章 · 获赞 2 · 访问量 1757 私信 关注
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: