好的,基本上我现在拥有的是:
XSD:
<?xml version="1.0"?>
<xsd:schema xmlns="test"
xmlns:xsd="http://www.w3.org/2001/XMLSchema"
targetNamespace="test"
elementFormDefault="qualified">
<xsd:complexType name="fields">
<xsd:choice minOccurs="1" maxOccurs="unbounded">
<xsd:element name="text">
<xsd:complexType>
<xsd:attribute name="id" type="xsd:string" use="required"/>
</xsd:complexType>
</xsd:element>
<xsd:element name="group">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="fields" type="fields"/>
</xsd:sequence>
<xsd:attribute name="id" type="xsd:string" use="required"/>
</xsd:complexType>
</xsd:element>
</xsd:choice>
</xsd:complexType>
<xsd:element name="root">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="fields" type="fields" minOccurs="0" maxOccurs="unbounded">
<xsd:key name="fieldId">
<xsd:selector xpath=".//*"/>
<xsd:field xpath="@id"/>
</xsd:key>
</xsd:element>
</xsd:sequence>
</xsd:complexType>
</xsd:element>
</xsd:schema>
XML:
<?xml version="1.0" encoding="UTF-8"?>
<root xmlns="test">
<fields>
<text id="asd"/>
<text id="sdf"/>
<group id="dfg">
<fields>
<text id="asd"/>
<text id="sdf"/>
</fields>
</group>
</fields>
</root>
显然,根据XSD,XML无效,因为ID有重复,但问题是,我希望id只能在自己的范围内进行验证,换句话说,这个应该失败:
<?xml version="1.0" encoding="UTF-8"?>
<root xmlns="test">
<fields>
<text id="asd"/>
<text id="asd"/>
</fields>
</root>
虽然这应该通过:
<?xml version="1.0" encoding="UTF-8"?>
<root xmlns="test">
<fields>
<text id="asd"/>
<group id="sdf">
<fields>
<text id="asd"/>
</fields>
</group>
</fields>
</root>
为了说清楚,我计划在解析XML时将父ID添加到子ID中,因此我不关心嵌套ID是否重复,而不是同样的范围,因为我希望能够达到类似的结果:
<?xml version="1.0" encoding="UTF-8"?>
<root xmlns="test">
<fields>
<group id="eventA_time">
<fields>
<text id="hour"/>
<text id="minute"/>
<text id="second"/>
</fields>
</group>
<group id="eventB_time">
<fields>
<text id="hour"/>
<text id="minute"/>
<text id="second"/>
</fields>
</group>
</fields>
</root>
答案 0 :(得分:0)
能够搜索亲戚:
更改:强>
<xsd:key name="fieldId">
<xsd:selector xpath=".//*"/>
<xsd:field xpath="@id"/>
</xsd:key>
以强>
<xsd:key name="fieldId">
<xsd:selector xpath="*"/>
<xsd:field xpath="@id"/>
</xsd:key>
答案 1 :(得分:0)
只需将选择器从.//*
更改为*
(或text
)。
答案 2 :(得分:0)
由于我没有得到完全符合我需要的答案,我只会发布一个版本的XSD,它可以正常工作,但由于某些部分被复制,仍然看起来很丑陋:
<?xml version="1.0"?>
<xsd:schema xmlns="test"
xmlns:xsd="http://www.w3.org/2001/XMLSchema"
targetNamespace="test"
elementFormDefault="qualified">
<xsd:complexType name="fields">
<xsd:choice minOccurs="1" maxOccurs="unbounded">
<xsd:element name="text">
<xsd:complexType>
<xsd:attribute name="id" type="xsd:string" use="required"/>
</xsd:complexType>
</xsd:element>
<xsd:element name="group">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="fields" type="fields" minOccurs="0" maxOccurs="unbounded">
<xsd:key name="innerFieldId">
<xsd:selector xpath="*"/>
<xsd:field xpath="@id"/>
</xsd:key>
</xsd:element>
</xsd:sequence>
<xsd:attribute name="id" type="xsd:string" use="required"/>
</xsd:complexType>
</xsd:element>
</xsd:choice>
</xsd:complexType>
<xsd:element name="root">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="fields" type="fields" minOccurs="0" maxOccurs="unbounded">
<xsd:key name="fieldId">
<xsd:selector xpath="*"/>
<xsd:field xpath="@id"/>
</xsd:key>
</xsd:element>
</xsd:sequence>
</xsd:complexType>
</xsd:element>
</xsd:schema>