文档章节

java中的xml解析时jaxp.properties文件问题

村长杨京京
 村长杨京京
发布于 2014/09/11 13:17
字数 1146
阅读 1566
收藏 6
工作中,使用JAVA的JAXP读取解析XML文件中,就碰到了一件奇件的事。在Web工程中,调试发现JAXP实际使用的是Xerces解析器,
可是,当将工程中的一个小Swing工具,与Web使用一样的jar包,打成一个可执行的jar包时,调试却发现JAXP实际使用的是Crimson
解析器,还会发现解析XML文件时出现错误,经过分析,发现Crimson解析器是Sun公司开发的(实际使用发现Crimson没有Xerces解析器稳定),
打包在JAVA_HOME/lib/dt.jar包中,这个dt.jar被设置在环境变量CLASSPATH中了,当运行可执行的jar包是,JAXP会使用CLASSPATH的解析器,
在Web工程中的War包则不会。
通过阅读JDK源码javax.xml.parsers.FactoryFinder,javax.xml.parsers.SAXParserFactory以及DocumentBuilderFactory发现JDK按照如下顺序:

1 系统属性javax.xml.parsers.DocumentBuilderFactory或javax.xml.parsers.SAXParserFactory

2 在jdk-dir/lib/jaxp.properties中设定的javax.xml.parsers.DocumentBuilderFactory或javax.xml.parsers.SAXParserFactory属性

3 运行时jar包中META-INF/services/javax.xml.parsers.DocumentBuilderFactory或javax.xml.parsers.SAXParserFactory文件中设定的值

4. 如果上面的解析器都没有找到,则使用Crimson。如果还没有。。。。。。那报ClassNotFound异常了。

通过JAXP查找解析器的顺序,我们可以使用下面方式来决定,我们使用的实际解析器,
1 在程序中写死实际的解析器

javax.xml.parsers.DocumentBuilderFactory factory= new org.apache.crimson.jaxp.DocumentBuilderFactoryImpl();
2 使用JAXP的 DocumentBuilderFactory 工厂类,如
javax.xml.parsers.DocumentBuilderFactory factory= javax.xml.parsers.DocumentBuilderFactory.newInstance();
再通过下面的方式来指定实际的解析器类
方法一:在运行java时,通过设置java -D javax.xml.parsers.DocumentBuilderFactory=new org.apache.crimson.jaxp.DocumentBuilderFactoryImpl
方法二:在程序中调用System.setProperty(“javax.xml.parsers.DocumentBuilderFactory”,” org.apache.crimson.jaxp.DocumentBuilderFactoryImpl”)
来设定实际的XML解析器.
方法三:编写一个jaxp.properties文件,在其中加入如下内容
javax.xml.parsers.DocumentBuilderFactory=org.apache.crimson.jaxp.DocumentBuilderFactoryImpl
再将此文件放入JAVA_HOME/lib/下
方法四:在打jar包下,在目录META-INF/下新建一个services目录,在此目录新建一个文件名为javax.xml.parsers.DocumentBuilderFactory的文件,
文件内容写上实际使用的解析器类,如写org.apache.crimson.jaxp.DocumentBuilderFactoryImpl
通过,上面,我们就可以对JAXP有一个比较深的了解。其实,JAVA中有许多这种思想的做法,这种思想,指的是什么的,就是平台无关性,发展到不依赖于具体的实现。
如我们熟悉的JNDI,JDBC,JAXP等。JNDI是抽像各种目录服务操作的类库,因为目录服务器厂商太多了,如SUN公司的ldapsdk,还有novell公司等等。JDBC是抽像各种数据库
操作的类库,因为数据库厂商也太多了,如ORACLE,SQLSERVER,MYSQL,INFORMIX等等,JAXP就是抽像各种XML解析器和转换器产品的类库,因为XML解析器和转换器产品够多
的了。

访问AIX系统中部署在OC4J中的web 模块的页面时遇到这个错误:
javax.xml.parsers.FactoryConfigurationError: Provider null could not be instantiated:
java.lang.NullPointerException
at javax.xml.parsers.SAXParserFactory.newInstance(Unknown Source)
at org.apache.commons.digester.Digester.getFactory(Digester.java:478)
at org.apache.commons.digester.Digester.getParser(Digester.java:683)
at org.apache.commons.digester.Digester.getXMLReader(Digester.java:891)
at org.apache.commons.digester.Digester.parse(Digester.java:1591)
at org.apache.struts.action.ActionServlet.initServlet(ActionServlet.java:1433)
at org.apache.struts.action.ActionServlet.init(ActionServlet.java:466)
at javax.servlet.GenericServlet.init(GenericServlet.java:256)
at com.evermind[Oracle Containers for J2EE 10g (10.1.3.0.0) ].server.http.HttpApplication.loadServlet(HttpApplication.java:2231)
at com.evermind[Oracle Containers for J2EE 10g (10.1.3.0.0) ].server.http.HttpApplication.findServlet(HttpApplication.java:4617)
……
或者这样的异常:
javax.servlet.jsp.JspException: Can't get definitions factory from context.
at org.apache.struts.taglib.tiles.InsertTag.processDefinitionName(InsertTag.java:583)
at org.apache.struts.taglib.tiles.InsertTag.createTagHandler(InsertTag.java:487)
at org.apache.struts.taglib.tiles.InsertTag.doStartTag(InsertTag.java:451)
at _welcome._jspService(_welcome.java:54)
[SRC:/welcome.jsp:4]

……
而当在Windows环境下部署时就没有问题。

这里是因为IBMAIX系统使用的是IBMJDK。而出现这个问题正是因为IBMSUNJDK的差异。 具体是因为 $JAVA_HOME/jre/lib/jaxp.properties 这个文件。

这个文件以key=value的形式配置和指定实际使用的XML解析器实现类(譬如:javax.xml.parsers.SAXParserFactory=org.apache.xerces.jaxp.SAXParserFactoryImpl)。在XML解析器初始化之前,JDK首先会搜索Systemproperties寻找解析器的配置项,如果没有则会搜索 $JAVA_HOME/jre/lib 路径下的 jaxp.properties 文件,如果还没有,接下来会在classpath上的.jar包中寻找,仍然没有的话就会使用默认的解析器。

实际上这个文件在SUNJDK中是不存在的。在找不到文件的情况下,最终将使用默认解析器。在IBMJDK中存在 jaxp.properties这个文件。但是这个文件中默认所有的配置项是注释掉的,所以在搜索到此处时,不再继续向下搜索,但是由于读取不到配置项,所以会返回null ,于是出现了上文的第一个错误。第二个异常大概是因为访问使用tiles框架的页面时,由于XML解析器初始化出错,所以tiles框架的配置文件也就读取不了了。

 

本文转载自:http://www.blogjava.net/hyhos/archive/2008/11/30/154606.html

上一篇: hashcode 和equals
下一篇: hotspot的源码结构
村长杨京京
粉丝 162
博文 878
码字总数 907544
作品 0
杭州
程序员
私信 提问
4个Java的常用工具,了解一下吧!

在现如今的互联网时代里,Java无疑是一种极为流行的开发语言,无论是程序界还是整个互联网行业势必带来很大的影响。不管是人才需求还是薪资水平上,Java的发展前景都是很乐观的。 关于Java的...

梦想远方_8e96
2018/06/15
0
0
【XML系列】详解JDOM解析XML

【XML系列】详解JDOM解析XML 一、前言 JDOM是Breet Mclaughlin和Jason Hunter两大Java高手的创作成果,2000年初,JDOM作为一个开放源代码项目正式开始研发。JDOM是一种解析XML的Java工具包。...

磊神Ray
2011/11/01
201
0
XML解析(DOM、SAX、JDOM和DOM4J)

众所周知,现在解析XML的方法越来越多,但主流的方法也就四种,即:DOM、SAX、JDOM和DOM4J 下面首先给出这四种方法的jar包下载地址 DOM:在现在的Java JDK里都自带了,在xml-apis.jar包里 SA...

拷贝忍者卡卡习
2017/01/18
31
0
java解析xml文件四种方式介绍、性能比较和基本使用方法

一、基本介绍: 1)DOM(JAXP Crimson解析器) DOM是用与平台和语言无关的方式表示XML文档的官方W3C标准。DOM是以层次结构组织的节点或信息片断的集合。这个层次结构允许开发人员在树中寻找特...

Candy_Desire
2014/08/20
1K
0
java解析xml的四种方法汇总

众所周知,现在解析XML的方法越来越多,但主流的方法也就四种,即:DOM、SAX、JDOM和DOM4J 下面首先给出这四种方法的jar包下载地址 DOM:在现在的Java JDK里都自带了,在xml-apis.jar包里 SA...

LYQ1990
2017/10/26
39
0

没有更多内容

加载失败,请刷新页面

加载更多

JDBC+C3P0+DBCP 基本使用

1.概述 这篇文章主要说了JDBC的基本使用,包括Statement,PreparedStatement,JDBC的连接,Mysql创建用户创建数据表,C3P0的连接与配置,DBCP的连接与配置. 2.mysql的处理 这里的JDBC使用Mysql作为...

Blueeeeeee
20分钟前
3
0
MVC Linux下开发及部署

linux使用的是 Ubuntu 64 位 18.04.2 LTS 首先复制C:\Program Files (x86)\Embarcadero\Studio\20.0\PAServer 下 LinuxPAServer20.0.tar.gz 到 linux 目录下 运行链接编译程序 delphi环境配置......

苏兴迎
今天
9
0
3.控件及其属性

1.文本 2.按钮

横着走的螃蟹
今天
7
0
安装Genymotion模拟器慢的解决方案

第一步点击下载, C:\Users\Administrator\AppData\Local\Genymobile\genymotion.log 中搜索 ova 会发现这个文件 使用迅雷下载即可. 在 虚拟机中导入这个.ova 文件 即可安装...

chenhongjiang
今天
5
0
4. 彤哥说netty系列之Java NIO实现群聊(自己跟自己聊上瘾了)

你好,我是彤哥,本篇是netty系列的第四篇。 欢迎来我的公从号彤哥读源码系统地学习源码&架构的知识。 简介 上一章我们一起学习了Java中的BIO/NIO/AIO的故事,本章将带着大家一起使用纯纯的N...

彤哥读源码
今天
7
0

没有更多内容

加载失败,请刷新页面

加载更多

返回顶部
顶部