XSD:指定一个选项必须至少有一个列表但不超过一个

时间:2011-11-22 09:43:23

标签: xsd xml-validation

这让我疯了好几个小时。我已经阅读了关于SO和互联网其他部分的所有相关XSD问题,但我的答案仍然存在。

我需要一个XML模式,它至少需要一个元素列表,但每个元素只能出现0或1次。

这与此问题类似: XML schema construct for "any one or more of these elements but must be at least one"

但我无法限制上限:我显然错误地使用了maxOccurs

这是我离开我的架构的地方:

<?xml version="1.0" encoding="UTF-8"?>
<xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema" elementFormDefault="qualified" attributeFormDefault="unqualified">
    <xs:complexType name="Selects">
        <xs:sequence minOccurs="2" maxOccurs="4">
        <xs:choice>
        <xs:element name="aaa" minOccurs="1" maxOccurs="1"/>
        <xs:element name="bbb" minOccurs="1" maxOccurs="1"/>
        <xs:element name="ccc" minOccurs="1" maxOccurs="1"/>
        <xs:element name="ddd" minOccurs="1" maxOccurs="1"/>
        </xs:choice>
    </xs:sequence>
    </xs:complexType>
    <xs:element name="baseElement">
        <xs:complexType>
        <xs:sequence>
        <xs:element name="MyChoice" type="Selects"/>
            </xs:sequence>
    </xs:complexType>
    </xs:element>
</xs:schema>

我在选择和元素上尝试了minOccursmaxOccurs没有运气。这是验证的XML,但我不希望它:

<?xml version="1.0" encoding="UTF-8"?>
<baseElement xsi:noNamespaceSchemaLocation="myTest.xsd"
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
    <MyChoice>
        <ddd/>
        <ddd/>
    </MyChoice>
</baseElement>

如果可能的话,这是我想要的一个例子:

<?xml version="1.0" encoding="UTF-8"?>
<baseElement xsi:noNamespaceSchemaLocation="myTest.xsd"
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
    <MyChoice>
        <ddd/>
        <aaa/>
        <ccc/>
    </MyChoice>
</baseElement>

我希望它抱怨多个ddd元素,但允许任何或所有其他元素按任何顺序排列。如果我在MyChoice下只有一个元素,那么我会收到错误,所以至少有些东西可以工作。

我做错了什么?如何防止多个相同元素进行验证?

更新

这是我的解决方案(来自以下回答的评论):

实际上,xs:所有人都做到了。我交换了所有选项,并为每个元素添加了minOccurs =“0”maxOccurs =“1”。使用xs:all,minOccurs必须为0或1且maxOccurs必须为1.感谢您的帮助 - 我现在很高兴!

1 个答案:

答案 0 :(得分:3)

只需将<xs:sequence minOccurs="2" maxOccurs="4">从选项周围移动到您想要进一步使用它的位置。 (你也可以删除min / max occurrence = 1,因为这是xs:choice所做的)

<xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema" elementFormDefault="qualified" attributeFormDefault="unqualified">
  <xs:complexType name="Selects">
    <xs:choice>
      <xs:element name="aaa" />
      <xs:element name="bbb" />
      <xs:element name="ccc" />
      <xs:element name="ddd" />
    </xs:choice>
  </xs:complexType>
  <xs:element name="baseElement">
    <xs:complexType>
      <xs:sequence minOccurs="2" maxOccurs="4">
        <xs:element name="MyChoice" type="Selects" />
      </xs:sequence>
    </xs:complexType>
  </xs:element>
</xs:schema>

这验证了以下内容:

<baseElement xsi:noNamespaceSchemaLocation="myTest.xsd" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
  <MyChoice>
    <bbb></bbb>
  </MyChoice>
  <MyChoice>
    <ccc></ccc>
  </MyChoice>
</baseElement>

<强>更新

我认为您已达到XSD所能达到的极限。除了为每一个可能的组合定义MyChoice类型的“版本”(然后需要不同的名称MyChoice1,MyChoice2等),我看不出你能做到这一点的任何方式

您也可以使用xs:all

  <xs:complexType name="Selects">
    <xs:all minOccurs=2 maxOccurs=4>
      <xs:element name="aaa" />
      <xs:element name="bbb" />
      <xs:element name="ccc" />
      <xs:element name="ddd" />
    </xs:all>
  </xs:complexType>

但这不会阻止你有四个<ddd/>