【问题标题】:XSD 1.1: Use of attribute only when another not required attribute is presentXSD 1.1:仅当存在另一个不需要的属性时才使用属性
【发布时间】:2021-01-10 08:08:56
【问题描述】:

我应该为一个简单的小型餐厅模拟器写一个xsd。 对于这个模拟器,我有许多被认为是食物的元素。其中一些不需要其他属性,因为它们已准备好使用。然而,这些食物元素中的一些需要准备,而一些需要准备的元素也应该只有在存在其他东西时才允许准备。为此,他们应该被赋予属性“条件”(见例子):

<food>
   <name>tea</name>
   <preparation>Ready to Go</preparation>
</food>

<food>
   <name>sandwich</name>
   <preparation time="2">Toaster</preparation>
</food>

<food>
   <name>noodles</name>
   <preparation time="5">Cooking-Pot</preparation>
</food>

<food>
   <name>lasagne</name>
   <preparation time="10" condition="noodles">Toaster</preparation>
</food>

我需要定义属性“条件”只能在属性“时间”存在时使用。所以像下面这样的元素应该是无效的:

<food>
   <name>toast</name>
   <preparation condition="noodles">Toaster</preparation>
</food>

此外,属性“条件”应该只能具有来自元素“名称”或“设备”的值(我不知道,如果我解决了那个,因为我无法解决第一个需求)。

到目前为止,我尝试使用断言来定义这两个需求。但遗憾的是它根本不起作用。任何时候都可以使用属性“条件”并给定任何随机值,因此它忽略了所有限制。或者编译器(我正在使用 Oxygen XML-Editor)总是抛出一个错误(元素 'food' ond schema type '#AnonType_foodmenues' 的断言评估没有成功)。 这是我的 xsd 文件的示例,用于进一步分析。

XSD:
<xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema" xmlns:vc="http://www.w3.org/2007/XMLSchema-versioning" elementFormDefault="qualified" vc:minVersion="1.1"> 
    <xs:element name="menues">
        <xs:complexType>
            <xs:sequence>
                <xs:element name="food" maxOccurs="unbounded" minOccurs="0">
                    <xs:complexType>
                        <xs:sequence>
                            <xs:element name="name">
                                <xs:simpleType>
                                    <xs:restriction base="xs:string">
                                        <xs:enumeration value="tea"/>
                                        <xs:enumeration value="sandwich"/>
                                        <xs:enumeration value="noodles"/>
                                        <xs:enumeration value="lasagne"/>
                                        <xs:enumeration value="pizza"/>
                                        <xs:enumeration value="juice"/>
                                        <xs:enumeration value="salat"/>
                                    </xs:restriction>
                                </xs:simpleType>
                            </xs:element>
                            <xs:element name="preparation">
                                <xs:complexType>
                                    <xs:simpleContent>
                                        <xs:extension base="device">
                                            <xs:attribute name="time">
                                                <xs:simpleType>
                                                    <xs:restriction base="xs:integer"/>
                                                </xs:simpleType>
                                            </xs:attribute>
                                            <xs:attribute name="condition" type="xs:string"/>
                                        </xs:extension>
                                    </xs:simpleContent>
                                </xs:complexType>
                            </xs:element>
                        </xs:sequence>
                        <xs:assert test="(preparation/@condition = (name, device)) or not (preparation/@condition)"/>
                        <xs:assert test="if (@condition) then (@time) else not (@condition)"/>
                    </xs:complexType>
                </xs:element>
            </xs:sequence>
        </xs:complexType>
    </xs:element>
    <xs:simpleType name="device">
        <xs:restriction base="xs:string">
            <xs:enumeration value="Ready to Go"/>
            <xs:enumeration value="Toaster"/>
            <xs:enumeration value="Cooking-Pot"/>
            <xs:enumeration value="Pan"/>
            <xs:enumeration value="Ofen"/>
        </xs:restriction>
    </xs:simpleType>
</xs:schema>

我在哪里犯错了? 由于这不起作用,我认为我的断言是错误的,但我无法弄清楚它们是放错了地方还是写错了。如何使属性“条件”只能在属性“时间”存在时使用? 非常感谢任何帮助。

【问题讨论】:

    标签: xml if-statement xsd attributes conditional-statements


    【解决方案1】:

    我能够弄清楚: 我只需要稍微改变断言。第一个将更改为&lt;xs:assert test="(@time) or not (@condition)"/&gt;,以便仅在存在“时间”时才允许使用属性“条件”。第二个我可以通过将属性“名称”概括为类型定义并在 xs:union 中重写“条件”属性类型来删除,如下所示:

    <xs:attribute name="condition">
       <xs:simpleType>
          <xs:union memberTypes="name device"/>
       </xs:simpleType>
    </xs:attribute>
    

    【讨论】:

      猜你喜欢
      • 2020-11-07
      • 2021-04-14
      • 1970-01-01
      • 1970-01-01
      • 2010-10-20
      • 1970-01-01
      • 2018-06-09
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多