查找给定类型的XML属性

时间:2015-04-16 17:16:02

标签: java xml xpath

给出如下架构:

<?xml version="1.0" encoding="utf-8"?>
<xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema" targetNamespace="http://my.namespace/version/1" xmlns:tns="http://my.namespace/version/1" elementFormDefault="qualified">
  <xs:simpleType name="isbn">
    <xs:restriction base="xs:string">
      <xs:pattern value="(\d{10}|\d{13})"/>
    </xs:restriction>
  </xs:simpleType>

  <xs:element name="inventory">
    <xs:complexType>
      <xs:all>
        <xs:element ref="tns:cd"/>
        <xs:element ref="tns:book"/>
      </xs:all>
    </xs:complexType>
  </xs:element>

  <xs:element name="book">
    <xs:complexType>
      <xs:attribute name="id" use="required" type="tns:isbn"/>
    </xs:complexType>
  </xs:element>

  <xs:element name="cd">
    <xs:complexType>
      <xs:attribute name="id" use="required" type="tns:isbn"/>
    </xs:complexType>  
  </xs:element>
</xs:schema>

以下相应的XML文件:

<?xml version="1.0" encoding="utf-8"?>
<inventory xmlns="http://my.namespace/version/1">
  <book id="1000000000"/>
  <cd id="1234567891234"/>
</inventory>

有没有办法使用XPath或其他一些基于查询的方法来选择isbn类型的所有属性?请注意,我不想按属性名称进行查询,而是查询模式中定义的类型。

1 个答案:

答案 0 :(得分:1)

要根据模式类型进行匹配或选择,您需要使用模式感知XSLT 2.0或更高版本或模式感知XQuery 1.0或更高版本,您需要确保在XSLT或XQuery中使用模式感知处理器(如Saxon的Enterprise Edition EE 9.然后,您可以使用attribute(*, prefix:isbn)根据类型选择属性。

一个简单的例子是

<?xml version="1.0" encoding="UTF-8" ?>
<xsl:transform xmlns:xsl="http://www.w3.org/1999/XSL/Transform" version="2.0"
  xmlns:xs="http://www.w3.org/2001/XMLSchema"
  xmlns:mns1="http://my.namespace/version/1" exclude-result-prefixes="xs mns1">

<xsl:import-schema>
<xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema" targetNamespace="http://my.namespace/version/1" xmlns:tns="http://my.namespace/version/1" elementFormDefault="qualified">
  <xs:simpleType name="isbn">
    <xs:restriction base="xs:string">
      <xs:pattern value="(\d{10}|\d{13})"/>
    </xs:restriction>
  </xs:simpleType>

  <xs:element name="inventory">
    <xs:complexType>
      <xs:all>
        <xs:element ref="tns:cd"/>
        <xs:element ref="tns:book"/>
      </xs:all>
    </xs:complexType>
  </xs:element>

  <xs:element name="book">
    <xs:complexType>
      <xs:attribute name="id" use="required" type="tns:isbn"/>
    </xs:complexType>
  </xs:element>

  <xs:element name="cd">
    <xs:complexType>
      <xs:attribute name="id" use="required" type="tns:isbn"/>
    </xs:complexType>  
  </xs:element>
</xs:schema>
</xsl:import-schema>


<xsl:template match="/">
    <xsl:variable name="ex1">
<inventory xmlns="http://my.namespace/version/1" xsl:validation="strict">
  <book id="1000000000"/>
  <cd id="1234567891234"/>
</inventory>
    </xsl:variable>

    <xsl:value-of select="$ex1//attribute(*, mns1:isbn)"/>

</xsl:template>
</xsl:transform>

http://xsltransform.net/nc4NzQF/1在线,用Saxon 9.5 EE进行测试。

这是为了说明导入模式的工作方式以及属性选择的工作原理,在现实生活中,您希望使用经过验证的输入文档而不是带有经过验证的文字结果元素的变量内容,但我不知道如何说服xsltransform.net验证输入文档,因此示例使用结果元素而不是输入元素。