转载:用Ant操作XML文件

1.14 用XMLTask操作XML(1)

本节作者:Brian Agnew

对于简单的文本搜索和替换操作,Ant的<replace>任务就够用了,但在现代Java框架中,用户更可能需要强大的XML操作能力来修改servlet描述符、Spring配置等。

XMLTask是Ant外部任务,它提供了强大的XML编辑工具,主要用于在构建/部署过程中创建和修改XML文件。

使用XMLTask的好处如下?

与Ant的<replace>任务不同,XMLTask使用XPath提供识别XML文档各个部分的能力,并且还能在这些位置插入、删除和复制XML。用户可以使用XPath简单地识别XML元素或者用谓词(predicate)执行更复杂的逻辑(如“查找有‘Y’属性的名为‘X’的元素……”)。

XMLTask了解XML,这意味着用户不能创建格式混乱的XML文档,XMLTask将处理字符编码问题,而<replace>不知道XML文档的编码需求。例如,<replace>允许用户不使用对应实体(“<”、“>”和“&”)就能将“<”、“>”和“&”等字符插入到XML文档中,从而可能破坏文档的良好格式。

为了执行XML操作,XMLTask不要求用户学习或使用XSLT,它使用直观的指令如insert、replace和remove。

XMLTask易于使用。可以访问其主页(注5)或者从Sourceforge上(注6)下载它。要使用XMLTask不需要精通XPath,但如果需要相关介绍,可以查阅http://www.zvon.org/(注7)中的入门教程。

示例

下面介绍一个简单的例子。假设用户想修改一个Spring配置,目的是开发、测试和发布版本而进行修改,并想要执行插入、替换和删除操作。

以下是一个简单的XMLTask任务:

1         <project name="xmltask-demo" default="main">

2          <!--xmltask.jar should be referenced via lib,
or in the ${ant.home}/lib or similar

3             --> <taskdef name="xmltask" classname="com.
oopsconsultancy.xmltask.ant.XmlTask"/>

4          

5          <!-- you may need to reference a local copy of
the DTD here if your XML

6                  documents specify one. See below for more info -->

7          <xmlcatalog id="dtd">

8              <dtd

9                 publicId="-//SPRING//DTD BEAN//EN"

10             location="./spring-1.0.dtd"/>

11       </xmlcatalog>

12       

13       <target name="main">

14         <xmltask source="spring-template.xml" dest="
spring.xml" preserveType="true">

15           <xmlcatalog refid="dtd"/>

16           <insert path="/beans" position="under">

17                <![CDATA[

18                  <bean id="bean-to-insert" class="com.
oopsconsultancy.example.Bean1">

19                     <constructor-arg index="0">

20                       ...

21                     </constructor-arg>

22                  </bean>

23                 ]]>

24           </insert>

25         </xmltask>

26        </target>

27      </project>

像引用任何外部任务一样,使用<taskdef>来引用XMLTask任务。

在<xmltask>任务中指定源XML文件和目标XML文件,XMLTask将从源XML中读取内容,应用用户所配置的XMLTask指令,然后将XML写入目标文件。

每条指令识别一组匹配的XML元素(使用XPath),并在每个元素上执行操作。例如,<insert>指令将在由XPath指定的所有匹配XML元素上执行插入操作(使用XPath可以将操作限制为第一个匹配元素、最后一个匹配元素,诸如此类)。

指令集将顺序执行,因此,可以先指定插入操作,然后指定替换操作,再指定删除操作。

以上示例在spring-template.xml文件中的<beans>根元素下插入了一个Spring bean定义,并将结果写入spring.xml文件。假设spring-template.xml文件是如下所示的空配置文件:

28      <?xml version="1.0" encoding="UTF-8"?>

29      <!DOCTYPE beans PUBLIC "-//SPRING//DTD BEAN//EN" "http://www.springframework.org/dtd /spring-beans.dtd">

30      <beans>

31      </beans>

在运行上面给出的<xmltask>任务后,用户的spring.xml文件将类似于以下形式:

32      <?xml version="1.0" encoding="UTF-8"?>

33      <!DOCTYPE beans PUBLIC "-//SPRING//DTD BEAN//EN"

34           "http://www.springframework.org/dtd /spring-beans.dtd">

35           <beans>

36           <bean id=”bean-to-insert” class=”com.oopsconsultany.example.Bean1”

37           dependency-check="default"

38           lazy-init="default" singleton="true">

39                   <constructor-arg index=”0”>

40                   ...

41                   </constructor-arg>

42           </bean>

43      </beans>

  1. (9票)

    AD:

    1.14 用XMLTask操作XML(2)

    注意,在DTD中指定的有默认值的属性将生成并插入到输出XML中(并将其相应设置为默认值 —— 如dependency-check、lazy-init和singleton)。

    不必一定在Ant构建文件中指定XML,可以从文件中引用它。例如,可以将bean定义存储在development-bean.xml文件中,并使用以下代码将development-bean.xml的内容插入到Spring配置中:

1         <insert path="/beans" position="under"
file="development-bean.xml">

到目前为止,这些操作都相对简单,但用户可以执行更复杂的操作。例如,如果想要修改以下Spring数据源bean的登录信息:

2         <bean id="ExampleDataSource" class="org.
apache.commons.dbcp.BasicDataSource"

3         destroy-method="close">

4         <property name="driverClassName" ref="db-driver-name"/>

5         <property name="url" value="..."/>

6         <property name="username" value=""/>

7         <property name="password" value=""/>

8         </bean>

可以使用<replace>操作插入来自${dev.username}和${dev.password}属性中的用户名和密码:

9         <xmltask source="spring-template.xml" dest="spring.xml" preserveType="true">

10        <replace path="/beans/bean[@id=‘
ExampleDataSource‘]/property[@name=‘username‘]/@value"

11        withText="${dev.username}"/>

12        <replace path="/beans/bean[@id=‘
ExampleDataSource‘]/property[@name=‘password‘]/@value"

13        withText="${dev.password}"/>

14      </xmltask>

注意,通过使用谓词,此示例使用XPath指定要修改哪个bean(ExampleDataSource),XPath表达式指定“查找有特定id的bean,在其下找到有给定名称的属性”,从而允许用户修改特定元素的属性。

也可以删除XML,例如,用户可能想要删除所有test bean:

15      <remove path="/beans/bean[contains(@id, ‘Test‘)]"/>

这将从用户的Spring配置中删除所有id中有test的bean。

DTDXMLTask

在以上示例中指定了一个DTD的本地版本。如果是在源文档中指定DTD,XMLTask需要访问该DTD执行实体替换。如果直接连接到了Internet,那么,XMLTask和其他工具可以透明地获得DTD。不过,如果没有直接连接到Internet或者连接速度有问题,可能将需要指定一个本地副本(或者告诉XMLTask该DTD不可用)。

这很简单,只需要指定一个Ant <xmlcatalog>标签。例如,以下代码指定了一个Servlet DTD和一个本地副本:

16      <xmlcatalog id="dtd">

17         <dtd publicId="-//Sun Microsystems,
Inc.//DTD Web Application 2.3//EN"

18            location="./servlet-2.3.dtd"

19         />

20      </xmlcatalog>

此段代码用特定的公共ID指定了DTD的一个本地副本(servlet-2.3.dtd)。

然后,在<xmltask>调用中引用该副本:

21      <xmltask

22         source="src/web.xml" dest="target/web.xml"

23         preserveType="true">

24        <xmlcatalog refid="dtd"/>

25          ...

输出文档应该使用哪个DTD取决于如何操作源文档。大多数情况下,目标文档将匹配源文档的DTD。在这种场景下,可以告诉XMLTask在目标文档中生成与源文档相匹配的DTD指令:

26      <xmltask

27      source="src/web.xml" dest="target/web.xml"

28      preserveType="true">

在其他情况下,如从头创建文档或者对源文档进行了大量修改,将需要指定DTD公共和系统标识符:

29      <!-- we‘re creating a 2.3 web.xml document from scratch -->

30      <xmltask

31         source="src/web.xml" dest="target/web.xml"

32         public="-//Sun Microsystems, Inc.//DTD Web Application 2.3//EN"

33         system="http://java.sun.com/dtd/web-app_2_3.dtd">

通过XMLTask驱动Ant

可以用XMLTask读取XML文件,并利用这一点为每个指定的XML元素调用不同的Ant目标,这样就能通过外部配置文件驱动构建的各个部分。该文件可能表示用户想要构建的环境、需要测试的类或者需要处理的文件目录等。

例如,假设需要运行一组测试类,这些类封装在一个配置XML文件中:

34      <environments>

35         <env name="Test Scenario 1" enabled="true">

36           <class>com.oopsconsultancy.example.TestScenario1</class>

37           <db>database1</db>

38          <results>development/test/scenario1.txt</results>

39         </env>

40         <env name="Test Scenario 2" enabled="true">

41           <class>com.oopsconsultancy.example.TestScenario2</class>

42           <db>database2</db>

43          <results>development/test/test_data_2.txt</results>

44         </env>

45      </environments>

每个环境都有一个测试类、一个测试数据库和一个结果文本文件。

可以使用XMLTask遍历此文件,并执行每个测试类以执行相应的测试:

46      <!-- XMLTask only needs a source here, since it‘s only reading -->

47      <xmltask source="environments.xml">

48         <call path="/environments/env[@enabled=‘true‘]" target="execute-tests">

49            <param name="class" path="class/text()"/>

50            <param name="db" path="db/text()" default="devDb"/>

51            <param name="results" path="results/text()"/>

52         </call>

53      </xmltask>

54

55      <target name="execute-tests">

56         <echo>Running ${class} against ${db}, results in ${results}</echo>

57         <!-- run the appropriate tests -->

58      </target>

对于由/environments/env标识的每个XML元素(enabled属性为true),XMLTask都将调用Ant的execute-tests目标,每个被调用的Ant目标都使用读取的XML文件内容设置其属性。每次调用execute-tests目标时,XMLTask都会将${class}属性设置为该XML元素指定的类、将${db}属性设置为该元素指定的数据库,同时还将${results}属性设置为所需的结果文件。

AD:

1.14 用XMLTask操作XML(3)

如果运行以上代码,将会看到以下输出:

1         Running com.oopsconsultancy.example.TestScenario1
against database1, results in

2          development/test/scenario1.txt

3         Running com.oopsconsultancy.example.TestScenario2
against database2, results in

4          development/test/test_data_2.txt

其他技巧

更改编码

可以更改XML文件的字符编码:

5         <xmltask source="windows-encoded.xml" dest="16bit-unicode-encoded.xml"

6         encoding="UnicodeBig"/>

UnicodeBig是16位Unicode编码(big-endian)的编码代码,有关XML支持的编码信息,请访问http://java.sun.com/j2se/1.5.0/docs/guide/intl/encoding.doc.html。这将在输出时把XML文档转换为16位Unicode编码的文档。注意,不必定义任何指令,因为XMLTask只是简单地读入文档再将其输出。

维护有注释的文档

使用XMLTask可去掉XML文件中的注释,这意味着用户可以维护有多个注释部分的配置文件,并在部署时去掉所需部分的注释。例如:

7         <configurations>

8          <!--

9          <configuration env="dev">

10       ...

11       </configuration>

12       -->

13       <!--

14       <configuration env="test">

15       ...

16       </configuration>

17       -->

18       <!--

19       <configuration env="prod">

20       ...

21       </configuration>

22       -->

23      </configurations>

24      <!--

25      <xmltask source="source.xml" dest="dest.xml" >

26       <uncomment path="/configurations/comment()[2]"/>

27       ...

28      </xmltask>

这启用了第二个注释部分(注意,XPath是从元素1而不是0开始索引元素的)。因此,每个被部署的文档都将有相同的注释部分,但只一个部分需要被取消注释,在必须比较部署的不同版本及其之间的差别时,这会使用户的工作轻松得多。

时间: 2024-10-08 09:30:18

转载:用Ant操作XML文件的相关文章

PHP操作XML文件学习笔记

原文:PHP操作XML文件学习笔记 XML文件属于标签语言,可以通过自定义标签存储数据,其主要作用也是作为存储数据. 对于XML的操作包括遍历,生成,修改,删除等其他类似的操作.PHP对于XML的操作方式很多,这次学习的是通过DOMDocument进行操作,其他的操作方法可以参考 http://www.oschina.net/code/snippet_110138_4727 1.对XML文件的遍历 通过DOMDocument对于XML文件的操作的方法:首先要实例化一个DOMDocument类的对

C#操作XML文件实例汇总

针对XML文件的操作是C#程序设计中非常常见的功能.本文即以实例展示了C#操作XML文件的几个常见的示例.具体如下: 1.返回节点下标 public static XmlDocument getDoc(String path)//加载xml文档 { XmlDocument doc = new XmlDocument(); doc.Load(path); return doc; } /// <summary> /// 返回找到的节点下标 /// </summary> /// <

利用XmlDocument操作XML文件

利用XmlDocument可以方便的操作XML文件. 1.操作XML文件基本方法 (1)添加对System.Xml的引用,并使用using语句添加引用: (2)假设要读取的XML文件如下: <?xml version="1.0" encoding="utf-8"?> <Students> <Student> <Name>张靓靓</Name> <Age>20</Age> <Hob

Java操作XML文件 dom4j 篇

在项目中,我们很多都用到了xml文件,无论是参数配置还是与其它系统的数据交互.今天就来讲一下Java 中使用dom4j来操作XML文件. 我们需要引入的包: //文件包 import java.io.ByteArrayOutputStream; import java.io.File; import java.io.FileWriter; //工具包 import java.util.Iterator; import java.util.List; //dom4j包 import org.dom

.Net常用技巧_操作xml文件教程(插入节点、修改、删除)

已知有一个XML文件(bookstore.xml)如下:     <?xml   version="1.0"   encoding="gb2312"?>     <bookstore>         <book   genre="fantasy"   ISBN="2-3631-4">             <title>Oberon's   Legacy</title&

springbatch操作XML文件

一.需求分析 使用Spring Batch对XML文件进行读写操作: 从一个xml文件中读取商品信息, 经过简单的处理, 写入另外一个xml文件中. 二.代码实现 1. 代码结构图: 2. applicationContext.xml <?xml version="1.0" encoding="UTF-8"?> <beans xmlns="http://www.springframework.org/schema/beans"

c#操作XML文件的通用方法

c#操作XML文件的通用方法 本文导读:我们在编写C#程序时,经常会通过C#访问XML文件,实现对XML文档的读写操作.下面为大家列出了通用的调用方法,大家可以将这些方法放在共用类里,其它的程序共享调用就可以了. 下面通过一个类将我们平时用c#操作XML文件的通用方法详细的介绍一下,关于asp.net C#操作xml文档实现代码,大家可以参考参考. c# 代码 1 sing System; 2 using System.Data; 3 using System.Configuration; 4

Asp.Net 操作XML文件的增删改查 利用GridView

不废话,直接上如何利用Asp.NET操作XML文件,并对其属性进行修改,刚开始的时候,是打算使用JS来控制生成XML文件的,但是最后却是无法创建文件,读取文件则没有使用了 index.aspx 文件 <%@ Page Language="C#" AutoEventWireup="true" CodeBehind="index.aspx.cs" Inherits="XmlManager.index" %> <!

使用dom4j操作xml文件的增删改

package day2.domx; import java.io.File; import java.io.FileOutputStream; import java.io.OutputStream; import org.dom4j.Document; import org.dom4j.Element; import org.dom4j.io.OutputFormat; import org.dom4j.io.SAXReader; import org.dom4j.io.XMLWriter;