最近项目要做不同系统之间相关数据的数据同步,实现方式为各个应用系统发送http请求到公共基础数据集市,采用xml进行数据封装传输。以前xml基本都用dom和SAX之类的,第一次接触XMLBeans,把自己用到的记录一下,请大家多指教。
XMLBeans是Apache的一个开源项目,可以从http://xmlbeans.apache.org/下载最新的版本,解压之后如下:
- xmlbean2.4.0
- +---bin
- +---docs
- +---lib
- +---samples
- +---schemas
XMLBeans使用步骤介绍:
- XMLBeans使用的准备工作:
- XMLBeans的使用需要将下载解压之后lib目录下的xbean.jar放入到项目的类路径上。
- 编译生成所需jar包还需将bin目录放入到环境变量classpath中,如:L:\XMLBeans\xmlbeans-2.4.0\bin
- 编写将要操作的javabean实体类的Schema文件,利用这个Schema文件,XMLBeans可以知道一个XML文件的结构以及约束。XMLBean将会产生一系列相关的Java Classes来实现对XML的操作。 而作为开发人员,则是利用XMLBean产生的Java Classes来完成对XML的操作而不需要SAX或DOM。 下面是员工基本信息的Schema文件ebi.xsd:
1 <?xml version="1.0" encoding="UTF-8"?> 2 <xsd:schema xmlns:xsd="http://www.w3.org/2001/XMLSchema"> 3 4 <xsd:include schemaLocation="CommonTypes.xsd"/> 5 6 <xsd:element name="ebiRequest" type="ebi_Request"/> 7 8 <!-- <Request>节点的类型定义 --> 9 <xsd:complexType name="ebi_Request"> 10 <xsd:sequence> 11 <xsd:element name="RequestInfo" type="fca_RequestInfo" minOccurs="1" maxOccurs="1"/> 12 <xsd:choice> 13 <xsd:element name="ebi" type="fca_ebi" minOccurs="1" maxOccurs="1"/> 14 </xsd:choice> 15 </xsd:sequence> 16 </xsd:complexType> 17 18 <xsd:complexType name="fca_ebi"> 19 <xsd:sequence> 20 <xsd:element name="stafNo" type="fca_Min6Max6String" minOccurs="1" maxOccurs="1"/> 21 <xsd:element name="stafNam" type="fca_Min0Max30String" minOccurs="0" maxOccurs="1"/> 22 <xsd:element name="stafSex" type="fca_Min1Max1String" minOccurs="0" maxOccurs="1"/> 23 <xsd:element name="idCardNo" type="fca_Min15Max18String" minOccurs="0" maxOccurs="1"/> 24 <xsd:element name="atchOrg" type="fca_Min6Max6String" minOccurs="0" maxOccurs="1"/> 25 <xsd:element name="atchDprt" type="fca_Min6Max6String" minOccurs="0" maxOccurs="1"/> 26 <xsd:element name="corspgEhrStafNo" type="fca_Min20Max20String" minOccurs="0" maxOccurs="1"/> 27 <xsd:element name="stafProp" type="fca_Min1Max1String" minOccurs="0" maxOccurs="1"/> 28 <xsd:element name="admiPrfn" type="fca_Min2Max2String" minOccurs="0" maxOccurs="1"/> 29 <xsd:element name="stafSts" type="fca_Min1Max1String" minOccurs="0" maxOccurs="1"/> 30 <xsd:element name="enblDat" type="fca_Min8Max8String" minOccurs="0" maxOccurs="1"/> 31 <xsd:element name="lastMantDat" type="fca_Min8Max8String" minOccurs="0" maxOccurs="1"/> 32 <xsd:element name="lastMantStafNo" type="fca_Min6Max6String" minOccurs="0" maxOccurs="1"/> 33 <xsd:element name="pubDelInd" type="fca_Min1Max1String" minOccurs="0" maxOccurs="1"/> 34 </xsd:sequence> 35 </xsd:complexType> 36 37 </xsd:schema>
其中<xsd:include schemaLocation="CommonTypes.xsd"/>包含公共应用的数据类型及请求数据头约束。如数据类型fca_Min6Max6String。
1 <!-- <RequestInfo>节点的类型定义 --> 2 <xsd:complexType name="fca_RequestInfo"> 3 <xsd:sequence> 4 <xsd:element name="SystemCode" type="fca_Min1Max10String" minOccurs="1" maxOccurs="1"/> 5 <xsd:element name="Password" type="fca_Min1Max10String" minOccurs="1" maxOccurs="1"/> 6 </xsd:sequence> 7 </xsd:complexType>
minOccurs和maxOccurs定义了数据节点在生成的xml中出现的最少和最多的次数。
3.根据编写的的xsd文件,通过dos命令生成xmlbeans操作所需的相应jar包:
scomp -src E:\src -out E:\src\com\openseven\xmlbeans\jar\openseven-xmlbeans.jar -compiler D:\Java\jdk1.6.0_10\bin\javac E:\src\com\openseven\xmlbeans\*.xsd E:\src\com\openseven\xmlbeans\syndicate.xsdconfig
scomp命令为第一步准备工作中我们放入环境变量bin目录下的。 -src为生成jar包中的源文件的输出目录,其中用到最后的syndicate.xsdconfig文件中定义相应的package,如下:
<xb:config xmlns:xb="http://xml.apache.org/xmlbeans/2004/02/xbean/config"> <xb:namespace> <xb:package>com.openseven.xmlbeans.src</xb:package> </xb:namespace> </xb:confi
最终生成源代码目录为E:\src\com\openseven\xmlbeans\src。-out为产生的class文件jar包输出目录, -compiler为java编译命令javac目录。
这里有一点要注意:-compiler命令所需的jdk目录中不能有空格,否则命令不能执行。
最后的*.xsd为要操作的xsd文件,即上面的ebi.xsd文件。通过命令生成的jar包就可以放到类路径上我们进行操作了。
首先,应用xmlbeans中的xmlOptions类生成相应参数数据,示例如下:
XmlOptions xmlOptions = new XmlOptions(); xmlOptions.setCharacterEncoding("UTF-8"); xmlOptions.setUseDefaultNamespace(); xmlOptions.setSavePrettyPrint();
1 //首先根据xmlOptions生成要发送的数据的xml对象RequestDocument 2 EbiRequestDocument ebi = EbiRequestDocument.Factory.newInstance(xmlOptions); 3 //根据提前规定好的xml格式添加相应节点信息,其中FcaRequestInfo为公共请求信息,包括请求的系统代码和密码,验证不通过将不能进行数据同步 4 EbiRequest ebiRequest = ebi.addNewEbiRequest(); 5 //添加<RequestInfo>节点 6 FcaRequestInfo ebiRequestInfo = ebiRequest.addNewRequestInfo(); 7 //添加<ebi>节点 8 FcaEbi ebi = ebiRequest.addNewEbi();
下面对生成的相应对象进行赋值操作,基于对象的set操作(示例只生成了两个stafNo和stafNam作为说明,其他属性未全部列出)
1 //设置<SystemCode>节点 2 ebiRequestInfo.setSystemCode("openseven"); 3 //设置<Password>节点 4 ebiRequestInfo.setPassword("000001"); 5 ebi.setStafNo("000003"); 6 ebi.setStafNam("stafNam")
以上代码对应生成的xml如下,对比参照,一目了然
1 ebiRequest> 2 <RequestInfo> 3 <SystemCode>openseven</SystemCode> 4 <Password>000001</Password> 5 </RequestInfo> 6 <ebi> 7 <stafNo>000003</stafNo> 8 <stafNam>stafNam</stafNam> 9 </ebi> 10 </ebiRequest>
可以根据xmlbeans提供的相应方法封装和解析相应的xml文件
1 EbiRequestDocument ebiDocument = EbiRequestDocument.Factory.parse(requestStr); 2 validateXml(ebiDocument); 3 EbiRequest request = ebiDocument.getEbiRequest();
validateXml可以对接收的xml进行格式校验
1 private void validateXml(XmlObject xmlObject) throws XmlSyndicateException { 2 List<XmlValidationError> errorList = new ArrayList<XmlValidationError>(); 3 XmlValidationError xmlFormatError = null; 4 XmlOptions xmlOptions = new XmlOptions(); 5 xmlOptions.setErrorListener(errorList); 6 boolean isValid = xmlObject.validate(xmlOptions); 7 if (!isValid) { 8 xmlFormatError = errorList.iterator().next(); 9 } else { 10 xmlFormatError = null; 11 } 12 if (xmlFormatError != null) { 13 int line = xmlFormatError.getLine(); 14 int column = xmlFormatError.getColumn(); 15 // Error 16 throw new XmlSyndicateException(SyndicateConst.XML_PARSE_ERROR, 17 SyndicateConst.XML_PARSE_ERROR_INFO 18 + xmlFormatError.getMessage(), line, column); 19 } 20 }
大家还可以参考一下文章http://youlong05.iteye.com/blog/87324