使用 Java 解析 XML 文件有许多成熟的工具,如 dom4j 等等。但在一些场景中,我们可能使用 Ant、Maven 等构建工具对多个 XML 文件进行合并,我们希望可以直接通过脚本文件,或者简单的程序就能完成这样的功能,那么使用 XSL 是一个非常不错的选择。本文将介绍通过简单的 Java 程序加上 XSL 文件来完成多个 XML 文件的合并操作。(XSL 是一种样式表语言,可用以描述如何显示一个 XML 文件)

背景

  1. Config.xml 文件的结构与 FinalConfig.xml 文件相似;
  2. 需要将 Config.xml 文件的内容合并到 FinalConfig.xml 文件;
  3. 若 FinalConfig.xml 文件中已存在 Config.xml 的内容,则覆盖。

目标:程序执行完成后,生成一个唯一的 XML 文件 FinalConfig.xml;

FinalConfig.xml 文件结构:

 <gameconfig>
<games>
<game>
<gameid>100</gameid>
<gamename>Fly to the Moon</gamename>
<gamedesc>This is Fly to the Moon</gamedesc>
</game>
<game>
<gameid>101</gameid>
<gamename>10 Miles</gamename>
<gamedesc>This is 10 Miles</gamedesc>
</game>
</games>
</gameconfig>

Config.xml 文件结构:

 <gameconfig>
<games>
<game>
<gameid>100</gameid>
<gamename>Fly to the Sun</gamename>
<gamedesc>This is Fly to the Sun</gamedesc>
</game>
</games>
</gameconfig>

我们假定 gameid 是固定值,不会变。在合并完成后,<gameid>为 100 的 node 被更新。希望得到新的 FinalConfig.xml 文件如下:

 <gameconfig>
<games>
<game>
<gameid>100</gameid>
<gamename>Fly to the Sun</gamename>
<gamedesc>This is Fly to the Sun</gamedesc>
</game>
<game>
<gameid>101</gameid>
<gamename>10 Miles</gamename>
<gamedesc>This is 10 Miles</gamedesc>
</game>
</games>
</gameconfig>

一、Java 调用程序

 private void mergeXml(File xslFile, File configXml, File finalConfigXml){
DocumentBuilderFactory dbFac = DocumentBuilderFactory.newInstance();
DocumentBuilder builder;
Document destDoc = null;
FileInputStream input;
try{
builder = dbFac.newDocumentBuilder();
destDoc = builder.parse(finalConfigXml);
if(!finalConfigXml.exists())
{
finalConfigXml.createNewFile();
}
input = new FileInputStream(xslFile);
StreamSource source = new StreamSource(input);
Transformer transformer = TransformerFactory.newInstance().newTransformer(source);
//为xsl文件设置变量"configXmlPath",将configXml文件的路径传递给xsl
transformer.setParameter("configXmlPath", configXml.getPath());
transformer.transform(new DOMSource(destDoc), new StreamResult(finalConfigXml));
}catch(Exception e) {
e.printStackTrace();
}
}

二、XSL 文件

 <?xml version="1.0" encoding="UTF-8"?>
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"> <xsl:output method="xml" indent="yes"/> <!-- pass the Config.xml file's path from Java code -->
<xsl:param name="configXmlPath"/>
<xsl:variable name="configXml" select="document($configXmlPath)"/> <xsl:template match="@* | node()">
<xsl:copy>
<xsl:apply-templates select="@* | node()"/>
</xsl:copy>
</xsl:template> <xsl:template match="/gamedata">
<xsl:copy>
<xsl:apply-templates select="games" mode="updateGames"/>
</xsl:copy>
</xsl:template> <xsl:template match ="games" mode="updateGames">
<xsl:variable name="gamesStr">
<xsl:for-each select="$configXml/gamedata/games/game">
<xsl:choose>
<xsl:when test="gameid">
<xsl:value-of select="concat('-',current()/gameid)"/>
</xsl:when>
</xsl:choose>
</xsl:for-each>
</xsl:variable>
<games>
<xsl:for-each select="game">
<xsl:if test="not(contains($gamesStr,gameid))">
<xsl:copy-of select="current()"/>
</xsl:if>
</xsl:for-each>
<xsl:apply-templates select="$configXml/gamedata/games/game" />
</games>
</xsl:template>
</xsl:stylesheet>

三、XSL 文件解析

1.Java 传入参数 “configXmlPath” 为 Config.xml 文件的路径

 <xsl:param name="configXmlPath"/> 

2.取出 Config.xml 文件中所有的 gameid,此处为增强处理,即 Config.xml 文件中可以存在多个 <game> 节点

 <xsl:variable  name="gamesStr">
<xsl:for-each select="$configXml/gamedata/games/game">
<xsl:choose>
<xsl:when test="gameid">
<xsl:value-of select="concat('-',current()/gameid)"/>
</xsl:when>
</xsl:choose>
</xsl:for-each>
</xsl:variable>

3.判断 FinalConfig.xml 的 <games> 子节点中是否存在当前的 gameid ,若不存在则复制

 <xsl:for-each select="game">
<xsl:if test="not(contains($gamesStr,gameid))">
<xsl:copy-of select="current()"/>
</xsl:if>
</xsl:for-each>

4.复制 Config.xml 文件中的所有 <game> 节点

<xsl:apply-templates select="$configXml/gamedata/games/game" />

(本文系从原博客迁移至此,并进行部分编辑。原文链接:http://thewaychung.iteye.com/blog/2072740)

Java+XSL合并多个XML文件的更多相关文章

  1. JAVA中通过Jaxp操作XML文件基础

    Java中有多种方式操作XML文件,目前讲一讲以SUN公司提供的DocumentBuilderFactory工厂类对象操作XML. 使用XML基本操作就是需要CRUD(增删改查),那么首先通过一个查询 ...

  2. Delphi调用JAVA的WebService上传XML文件(XE10.2+WIN764)

    相关资料:1.http://blog.csdn.net/luojianfeng/article/details/512198902.http://blog.csdn.net/avsuper/artic ...

  3. 使用java代码动态配置与xml文件结合的方式使用mybatis-generator生成代码配置

    1.使用java代码动态配置与xml文件结合的方式使用mybatis-generator生成代码配置 2.上代码:在resources目录下新建:generatorConfiguration.xml文 ...

  4. JAVA中使用DOM解析XML文件

    XML是一种方便快捷高效的数据保存传输的格式,在JSON广泛使用之前,XML是服务器和客户端之间数据传输的主要方式.因此,需要使用各种方式,解析服务器传送过来的信息,以供使用者查看. JAVA作为一种 ...

  5. java中采用dom4j解析xml文件

    一.前言 在最近的开发中用到了dom4j来解析xml文件,以前听说过来解析xml文件的几种标准方式:但是从来的没有应用过来,所以可以在google中搜索dmo4j解析xml文件的方式,学习一下dom4 ...

  6. Spring MVC框架下在java代码中访问applicationContext.xml文件中配置的文件(可以用于读取配置文件内容)

    <bean id="propertyConfigurer" class="com.****.framework.core.SpringPropertiesUtil& ...

  7. java代码用dom4j解析xml文件的简单操作

    时间: 2016/02/17 目标:为telenor的ALU Femto接口写一个采集xml文件并解析出locationName标签里的值,然后更新到数据库中. 从网上搜了下,有四种常用的解析xml的 ...

  8. java中利用dom4j解析XML文件

    官网下载Dom4j地址:https://dom4j.github.io/ 注意:使用Dom4j开发,需下载dom4j相应的jar文件 题目:后台利用dom4j解析student.xml文件,并返回Li ...

  9. java struts2入门学习--基于xml文件的声明式验证

    一.知识点总结 后台验证有两种实现方式: 1 手工验证顺序:validateXxx(针对Action中某个业务方法验证)--> validate(针对Action中所有的业务方法验证) 2 声明 ...

随机推荐

  1. springboot(三):Spring boot中Redis的使用

    spring boot对常用的数据库支持外,对nosql 数据库也进行了封装自动化. redis介绍 Redis是目前业界使用最广泛的内存数据存储.相比memcached,Redis支持更丰富的数据结 ...

  2. windows上安装jdk

    1.下载jdk安装包 jdk官网   http://www.oracle.com/technetwork/java/javase/downloads/index.html 2.安装jdk 傻瓜式下一步 ...

  3. 自定义控件pickView

    package com.example.healthembed.util; import java.util.ArrayList; import java.util.List; import java ...

  4. Ultimus BPM 房地产与建筑行业应用解决方案

    Ultimus BPM 房地产与建筑行业应用解决方案 行业应用需求 房地产与建筑行业客户业务特点是集团化管控,多区域.多项目.多业态管理,而行业业务往往项目周期长,涉及专业复杂,客户越来越重视管理和跟 ...

  5. 第 10 章 MySQL Server 性能优化

    前言: 本章主要通过针对MySQL Server(mysqld)相关实现机制的分析,得到一些相应的优化建议.主要涉及MySQL的安装以及相关参数设置的优化,但不包括mysqld之外的比如存储引擎相关的 ...

  6. 开涛spring3(4.3) - 资源 之 4.3 访问Resource

    4.3.1  ResourceLoader接口 ResourceLoader接口用于返回Resource对象:其实现可以看作是一个生产Resource的工厂类. public interface Re ...

  7. 元类(meta class)

    元类(meta class),这个名字想必很多人都听过,网上也有很多关于元类的介绍,今天我就按照自己这两天的理解来简单探讨一下这个玩意,有误之处还望指出. 首先,下载objc源码,源码地址:https ...

  8. 移动端车牌识别——可以嵌入智能手机系统里的新OCR识别技术

    移动端车牌识别技术,是在OCR光学字符识别技术的基础上研发的用来识别汽车号牌特征信息的图像识别技术.在国内,该项技术由北京易泊时代携手清华大学成功地将"国家863计划"项目成果-- ...

  9. 总结scala(一)

    由于笔记太多,分为了几部分,进入我的博客,查看其它的笔记 scala:面向对象,函数式编程 一.声明变量 1.变量的类型 Byte,Char,Short,Int,Long,Float,Double,B ...

  10. Java经典编程题50道之八

    求s=a+aa+aaa+aaaa+aa...a的值,其中a是一个数字.例如2+22+222+2222+22222(此时共有5个数相加),几个数相加由键盘控制. public class Example ...