2

我有一个 XML,它可以包含任何元素,例如:

<AnyElements>
  <Any1 id="any1" />
  <Any2 id="any2" />
  ...
</AnyElements>

但是id属性是强制性的。

我如何定义这样的xsd?

<xs:element name="AnyElements" type="AnyRootType" />
<xs:complexType name="AnyRootType">
  <xs:sequence>
    <xs:any type="AnyChildType" minOccurs="1" maxOccurs="unbounded"/>
  </xs:sequence>
</xs:complexType> 

<xs:complexType name="AnyChildType">
  <xs:attribute ref="id" use="required"/>
</xs:complexType>

<xs:attribute name="id" type="xs:string"/>
4

1 回答 1

0

这完全取决于您将如何定义处理模型。以下是您需要首先考虑的一些事项。

any粒子不能被类型约束。它带有一个名为skipprocessContentslax和默认值strict的属性。一旦您确切理解了它的含义,那么使用skip仅仅意味着您将无法强制执行您的强制属性 - 处理器将执行此操作,“跳过”。如果你设置它lax,那么它只会在描述内容的 XSD 实际可用时才处理它,否则它会跳过;第三个选项strict,要求描述此额外内容的 XSD 可用 - period。

因此,any只有在验证期间描述“任何”的 XSD 可用时,才能使粒子工作。我想到的选项有点限制,但它的优点是最接近 any 的“精神”,因为它不必从特定的基本类型派生或引用某些属性;为此,类似于您的要求的关键约束:

    <xsd:key name="ofid">
        <xsd:selector xpath="*"/>
        <xsd:field xpath="@id"/>
    </xsd:key>

实际上,键使属性成为必需。缺点可能是每个值也必须是唯一的。也许有一个名为 的属性id,这是预期的;相反,如果您希望将模式应用于诸如 之类的东西age,那么它就行不通了。

如果您认为 XSD 在运行时可用是可以接受的,那么其他替代方案可能包括使用抽象元素或具有抽象类型的元素。好消息是它会带来更严格的方法(您将从一开始就明确设置约束),并且不会设置值约束的唯一性。不利的一面可能是它创建了与另一个描述“合同”的 XSD 的耦合 - 您的强制属性。

更新:根据您的评论,以下是基于替代组的替代方案。我尝试尽可能多地保留旧的 XSD 组件名称。

Contract.xsd:这包含您的合同的组成部分。它基本上描述了您的替代小组的负责人;它表明需要一个 id 属性。

<?xml version="1.0" encoding="utf-8" ?>
<!--XML Schema generated by QTAssistant/XML Schema Refactoring (XSR) Module (http://www.paschidev.com)-->
<xsd:schema elementFormDefault="qualified" xmlns:xsd="http://www.w3.org/2001/XMLSchema">
    <xsd:complexType name="AnyChildType" abstract="true">
        <xsd:attribute name="id" use="required"/>
    </xsd:complexType>

    <xsd:element name="AnyElement" abstract="true" type="AnyChildType"/>
</xsd:schema>

GenericInstance.xsd:它描述了“通用”文档的根。它在您定义的根元素的上下文中“集成”您的合同。

<?xml version="1.0" encoding="utf-8" ?>
<!--XML Schema generated by QTAssistant/XML Schema Refactoring (XSR) Module (http://www.paschidev.com)-->
<xsd:schema elementFormDefault="qualified" xmlns:xsd="http://www.w3.org/2001/XMLSchema">
    <xsd:include schemaLocation="Contract.xsd"/>

    <xsd:element name="AnyElements" type="AnyRootType"/>
    <xsd:complexType name="AnyRootType">
        <xsd:sequence>
            <xsd:element ref="AnyElement" maxOccurs="unbounded"/>
        </xsd:sequence>
    </xsd:complexType>
</xsd:schema>

SpecificInstance1.xsd:特定合约。

<?xml version="1.0" encoding="utf-8" ?>
<!--XML Schema generated by QTAssistant/XML Schema Refactoring (XSR) Module (http://www.paschidev.com)-->
<xsd:schema elementFormDefault="qualified" xmlns:xsd="http://www.w3.org/2001/XMLSchema">
    <xsd:include schemaLocation="Contract.xsd"/>

    <xsd:element name="SomeElement1" substitutionGroup="AnyElement">
        <xsd:complexType>
            <xsd:complexContent>
                <xsd:extension base="AnyChildType">
                    <xsd:annotation>
                        <xsd:documentation>Any content goes.</xsd:documentation>
                    </xsd:annotation>
                </xsd:extension>
            </xsd:complexContent>
        </xsd:complexType>
    </xsd:element>
</xsd:schema>

SpecificInstance2.xsd:另一个合同(显示不同的创作风格)。

<?xml version="1.0" encoding="utf-8" ?>
<!--XML Schema generated by QTAssistant/XML Schema Refactoring (XSR) Module (http://www.paschidev.com)-->
<xsd:schema elementFormDefault="qualified" xmlns:xsd="http://www.w3.org/2001/XMLSchema">
    <xsd:include schemaLocation="Contract.xsd"/>

    <xsd:element name="SomeElement2" substitutionGroup="AnyElement" type="SomeElement2Type"/>
    <xsd:complexType name="SomeElement2Type">
        <xsd:complexContent>
            <xsd:extension base="AnyChildType">
                <xsd:annotation>
                    <xsd:documentation>Any content goes.</xsd:documentation>
                </xsd:annotation>
            </xsd:extension>
        </xsd:complexContent>
    </xsd:complexType>
</xsd:schema>

从视觉上看,这就是它们是如何联系在一起的。您可以看到 XSD 之间的耦合保持在最低限度。

在此处输入图像描述

一个示例 XML,在您的通用实例和特定实例定义的范围内有效。

<?xml version="1.0" encoding="utf-8" standalone="yes"?>
<!-- Sample XML generated by QTAssistant (http://www.paschidev.com) -->
<AnyElements xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
    <SomeElement1 id="1"/>
    <SomeElement2 id="1"/>
</AnyElements>

如果您仅限于使用一个 XSD 验证您的 XML,那么下面将是一个 XSD:

<?xml version="1.0" encoding="utf-8" ?>
<!--XML Schema generated by QTAssistant/XML Schema Refactoring (XSR) Module (http://www.paschidev.com)-->
<xsd:schema elementFormDefault="qualified" xmlns:xsd="http://www.w3.org/2001/XMLSchema">
    <xsd:include schemaLocation="GenericInstance.xsd"/>
    <xsd:include schemaLocation="SpecificInstance1.xsd"/>
    <xsd:include schemaLocation="SpecificInstance2.xsd"/>
</xsd:schema>

我已经使用在 .NET 上运行的 XSD 1.0 测试了上述内容;能够在 XSD 1.1 或其他 XSD 处理器中的特定功能上运行将使我所说的某些内容无效。

于 2012-10-01T16:29:29.403 回答