XML文件的读取
设有如下applicationContext.xml文件,bean之间的依赖关系如下,即在类FruitServiceImpl中有一个FruitDAO属性,该属性没有被实例化,需要通过解析这个配置文件来获得其实例化对象。
<?xml version="1.0" encoding="utf-8"?>
<!--id可以随便取,但是ref的值要与id一致,才能正确解析出依赖关系-->
<beans>
<bean id="fruitDAO" class="com.rolin.fruit.dao.impl.FruitDAOImpl"/>
<bean id="fruitService" class="com.rolin.fruit.service.impl.FruitServiceImpl">
<property name="fruitDAO" ref="fruitDAO"/>
</bean>
</beans>
首先读文件存入ducument中
InputStream inputStream = getClass().getClassLoader().getResourceAsStream("applicationContext.xml");
DocumentBuilderFactory documentBuilderFactory = DocumentBuilderFactory.newInstance();
DocumentBuilder documentBuilder = documentBuilderFactory.newDocumentBuilder();
Document document = documentBuilder.parse(inputStream);
获取节点列表
Map<String, Object> beanMap = new HashMap<>();
NodeList beanNodeList = document.getElementsByTagName("bean"); // 获取bean节点列表
// 获取所有bean节点,没有组装bean之间的依赖(即没有对里面的property节点做处理)
for (int i = 0; i < beanNodeList.getLength(); i++) {
Node beanNode = beanNodeList.item(i);
if (beanNode.getNodeType() == Node.ELEMENT_NODE) { // 判断是否是元素节点
Element beanElement = (Element) beanNode;
String beanId = beanElement.getAttribute("id"); // 即得到“fruitDAO”
String className = beanElement.getAttribute("class"); 即得到“com.rolin.fruit.dao.impl.FruitDAOImpl”
Object beanObj = null;
beanObj = Class.forName(className).newInstance(); // 通过反射创建对象实例
beanMap.put(beanId, beanObj); // Map<String, Object> 对象,用于存放解析完的对象实例映射
}
}
解析<bean>之间的依赖
for (int i = 0; i < beanNodeList.getLength(); i++) {
Node beanNode = beanNodeList.item(i); //<bean></bean>节点
if (beanNode.getNodeType() == Node.ELEMENT_NODE) {
Element beanElement = (Element) beanNode;
String beanId = beanElement.getAttribute("id");
NodeList beanChildList = beanElement.getChildNodes(); // <bean>节点里的子节点列表
for (int j = 0; j < beanChildList.getLength(); j++) {
Node beanChildNode = beanChildList.item(j);
if (beanChildNode.getNodeType() == Node.ELEMENT_NODE && "property".equals(beanChildNode.getNodeName())) { // 是否是元素节点,且节点名为“properties”
Element propertyElement = (Element) beanChildNode;
String propertyName = propertyElement.getAttribute("name");
String propertyRef = propertyElement.getAttribute("ref"); //propertyRef 依赖的对象名(与<bean>节点里的id名对应)
// 通过映射的对象名ref找到存储在beanMap的实例
Object refObj = beanMap.get(propertyRef); // 这里就是通过“fruitDAO”这个key找到对应的FruitDAOImpl实例
Object beanObj = beanMap.get(beanId); // 取出FruitServiceImpl的对象实例
// 通过反射机制获得类中的属性,并将该属性的值从原来的null变为对象实例
Class beanClazz = beanObj.getClass();
Field propertyField = beanClazz.getDeclaredField(propertyName);
propertyField.setAccessible(true); //对所有访问权限的域都可以做处理
propertyField.set(beanObj, refObj); //set(对象实例,该对象里的属性要替换成的新值)
}
}
}
}
然后就可以拿beanMap做后续的处理
Properties文件的读取
设有如下的数据库连接配置文件jdbc.properties,需要读取里面的值与数据库建立连接
# mysql8
driver=com.mysql.cj.jdbc.Driver
url=jdbc:mysql:///myschool?serverTimezone=Hongkong
username=root
password=123456
读取并加载文件
InputStream inputStream = getClass().getClassLoader().getResourceAsStream(jdbc.properties);
Properties properties = new Properties();
properties.load(inputStream);
String driver = properties.getProperty("driver");
String url = properties.getProperty("url");
String username = properties.getProperty("username");
String password = properties.getProperty("password"):