我想创建一个具有以下约束的XML模式:
list
。list
包含一组node
元素。node
元素可以具有value
属性。node
元素可以包含value
元素。node
元素只能包含(和完全)一个value
属性或value
元素。以下是验证上述约束的有效XML示例:
<?xml version="1.0" ?>
<list>
<node id="1" value="A" />
<node id="2">
<value>B</value>
</node>
</list>
我尝试了以下XSD架构:
<xs:schema attributeFormDefault="unqualified" elementFormDefault="qualified" xmlns:xs="http://www.w3.org/2001/XMLSchema">
<xs:element name="list">
<xs:complexType>
<xs:sequence>
<xs:element name="node" maxOccurs="unbounded" minOccurs="0">
<xs:complexType mixed="true">
<xs:sequence>
<xs:element type="xs:string" name="value" minOccurs="0"/>
</xs:sequence>
<xs:attribute type="xs:byte" name="id" use="optional"/>
<xs:attribute type="xs:string" name="value" use="optional"/>
</xs:complexType>
</xs:element>
</xs:sequence>
</xs:complexType>
</xs:element>
</xs:schema>
此XSD架构验证我的第一个和第二个约束,但不验证第三个约束。
以下XML示例根据我的约束无效,但是它对我之前的XSD架构有效。
<?xml version="1.0" ?>
<list>
<node id="2" value="A" /> <!-- valid -->
<node id="4">
<value>D</value>
</node><!-- valid -->
<node id="1" /><!-- not valid, missing value -->
<node id="3" value="B">
<value>C</value>
</node><!-- not valid, both attribute and element are declared -->
</list>
如何更改架构以验证所有约束?
提前致谢。
答案 0 :(得分:4)
使用XSD 1.0无法做到这一点。
XSD 1.1应该可以使用断言:
<xs:assert test="not(@value and value)"/>
如果@value
和value
都存在则失败。要检查是否只有一个属性或子元素使用:
<xs:assert test="count((value, @value))=1"/>
正如Michael Kay在评论中所建议的那样。
可能可以使用Schematron等其他一些XML验证技术。
答案 1 :(得分:0)
您可以使用required元素创建第一个类型,使用required元素创建第二个类型。然后使用包含两种类型的choice compositor。