以前从来没有用过 schema, 这次希望能给我的 xml 文件加上 namespace, schema, 然后用 xslt 转换成 html, 没想到花了不少功夫。现在我把工作正常的结果记录下来,希望对大家有些帮助。
先来看看我的 xml 文件。打算用来定义网页的菜单。
1<menu_items>
2<menu_item href="index.html" image="images/A1.gif" name="首页"></menu_item>
3<menu_item href="ep.html" image="images/A2.gif" name="新闻">
4<menu_item href="ep.html" image="images/A2.gif" name="国内新闻"></menu_item>
5</menu_item>
6</menu_items>
很简单的 xml 文件,抛开弯路不提,用 xmlspy 的 Generate Schema 功能自动生成 schema 文件,然后做些小修改,结果如下:
1<xs:schema targetnamespace=" http://www.hz-sp.com/2005/XMLSchema-menu " xmlns=" http://www.hz-sp.com/2005/XMLSchema-menu " xmlns:xs=" http://www.w3.org/2001/XMLSchema ">
2<xs:element name="menu_item">
3<xs:complextype>
4<xs:sequence>
5<xs:element minoccurs="0" ref="menu_item"></xs:element>
6</xs:sequence>
7<xs:attribute name="name" type="xs:string" use="required"></xs:attribute>
8<xs:attribute name="href" type="xs:anyURI" use="optional"></xs:attribute>
9<xs:attribute name="image" type="xs:anyURI" use="optional"></xs:attribute>
10</xs:complextype>
11</xs:element>
12<xs:element name="menu_items">
13<xs:complextype>
14<xs:sequence>
15<xs:element maxoccurs="unbounded" ref="menu_item"></xs:element>
16</xs:sequence>
17</xs:complextype>
18</xs:element>
19</xs:schema>
其中, http://www.hz-sp.com/2005/XMLSchema-menu 是我的namespace. 然后在xml中用xmlspy 的 Assign Schema 功能指定这个 xsd ,xml 中的根节点 menu_items 被为:
1<menu_items xmlns=" http://www.hz-sp.com/2005/XMLSchema-menu " xmlns:xsi=" http://www.w3.org/2001/XMLSchema-instance " xsi:schemalocation=" http://www.hz-sp.com/2005/XMLSchema-menu
2menu.xsd">
3
4接下来创建 xslt 文件,同样只给出正确的结果:
5
6<?xml version="1.0" encoding="GB2312"?>
7<xsl:stylesheet version="2.0" xmlns=" http://www.w3.org/1999/xhtml " xmlns:fn=" http://www.w3.org/2004/07/xpath-functions " xmlns:xdt=" http://www.w3.org/2004/07/xpath-datatypes " xmlns:xs=" http://www.w3.org/2001/XMLSchema " xmlns:xsl=" http://www.w3.org/1999/XSL/Transform " xpath-default-namespace=" http://www.hz-sp.com/2005/XMLSchema-menu ">>
8<xsl:output encoding="GB2312" indent="yes" method="html" version="4.0"></xsl:output>
9<xsl:template match="mm:menu_items" xmlns:mm=" http://www.hz-sp.com/2005/XMLSchema-menu ">
10<table border="0" cellpadding="0" cellspacing="0" width="900">
11<tr>
12<xsl:for-each select="mm:menu_item">
13<a href=" {@href }">
14<img border="0" height="57" src=" {@image }" width="113"/>
15</a>
16</xsl:for-each>
17</tr>
18</table>
19</xsl:template>
20</xsl:stylesheet>
21
22令人恼火的是,xpath-default-namespace=" http://www.hz-sp.com/2005/XMLSchema-menu " 对 xsl:template 的 match 没有效果,估计match 中并非 xpath。但是这个属性对 for-each 中的 select 同样没有起作用,这就比较奇怪了,估计我还没有理解这个属性该怎么使用。</menu_items>