Проблема при использовании расширения в схеме XML - PullRequest
0 голосов
/ 20 февраля 2020

Мне нужно создать схему XML, которая расширяет простые типы, чтобы я мог добавить атрибут для последующего использования в моем коде (этот атрибут не будет использоваться в сгенерированном XML). Это должно быть расширение, так как я должен установить sh некоторые ограничения для этих типов.

Проблема: msg_1 и msg_2 должны иметь несколько элементов с одинаковыми именами, и это вызывает ошибку.

Ошибка: согласована с cos-элементом: ошибка для типа '#AnonType_msg'. В группе моделей появляются несколько элементов с именем «Код», имеющих разные типы.

Мне известно, что изменение имен этих элементов приведет к решению проблемы, но, к сожалению, они должны быть одинаковыми.

Вот код:

<xsd:element name="msg">
    <xsd:complexType>
        <xsd:sequence>
            <xsd:group ref="header"/>    
            <xsd:choice>
                <xsd:group ref="msg_1"/>
                <xsd:group ref="msg_2"/>
            </xsd:choice>
        </xsd:sequence>
        <xsd:attribute name="IdMsg" type="IdM" use="required"/>
    </xsd:complexType>
</xsd:element>

<xsd:group id="M39" name="msg_1">
    <xsd:sequence>
        <xsd:element name="Code">
            <xsd:complexType>
                <xsd:simpleContent>
                    <xsd:extension base="Code">
                        <xsd:attribute name="compact" use="prohibited"/>
                    </xsd:extension>
                </xsd:simpleContent>
            </xsd:complexType>
        </xsd:element>
        <xsd:element name="ID">
            <xsd:complexType>
                <xsd:simpleContent>
                    <xsd:extension base="ID">
                        <xsd:attribute name="compact" use="prohibited"/>
                    </xsd:extension>
                </xsd:simpleContent>
            </xsd:complexType>
        </xsd:element>
   </xsd:sequence>
</xsd:group>
<xsd:group id="M40" name="msg_2">
    <xsd:sequence>
        <xsd:element name="Code">
            <xsd:complexType>
                <xsd:simpleContent>
                    <xsd:extension base="Code">
                        <xsd:attribute name="compact" use="prohibited"/>
                    </xsd:extension>
                </xsd:simpleContent>
            </xsd:complexType>
        </xsd:element>
        <xsd:element name="ID">
            <xsd:complexType>
                <xsd:simpleContent>
                    <xsd:extension base="ID">
                        <xsd:attribute name="compact" use="prohibited"/>
                    </xsd:extension>
                </xsd:simpleContent>
            </xsd:complexType>
        </xsd:element>
    </xsd:sequence>
</xsd:group>

<xsd:simpleType name="IdM">
    <xsd:restriction base="xsd:unsignedByte">
        <xsd:minInclusive value="29"/>
        <xsd:maxInclusive value="42"/>
    </xsd:restriction>
</xsd:simpleType>
<xsd:simpleType name="ID">
    <xsd:restriction base="xsd:unsignedByte">
        <xsd:minInclusive value="0"/>
        <xsd:maxInclusive value="255"/>
    </xsd:restriction>
</xsd:simpleType>
<xsd:simpleType name="Code">
    <xsd:restriction base="xsd:unsignedByte">
        <xsd:minInclusive value="0"/>
        <xsd:maxInclusive value="13"/>
    </xsd:restriction>
</xsd:simpleType>
<xsd:group id="M2" name="header">
    <xsd:sequence>
        <xsd:element fixed="2" name="Version" type="xsd:unsignedInt"/>
        <xsd:element name="Timer" type="xsd:unsignedLong"/>
    </xsd:sequence>
</xsd:group>

Есть ли обходной путь?

Обновление: утверждения не соответствуют действительности. По сути, у меня есть два разных сообщения (группы), разделяющие некоторые параметры (дочерние элементы).

Полагаю, что пространства имен могли бы сработать, но я стараюсь этого избегать, поскольку предпочтительнее иметь только 1 файл .xsd.

Я получил часть о двусмысленности и т. Д. c, но он не отвечает, почему следующий код подтверждает правильность. Вот код:

<xsd:element name="msg">
    <xsd:complexType>
        <xsd:sequence>
            <xsd:group ref="header"/>    
            <xsd:choice>
                <xsd:group ref="msg_1"/>
                <xsd:group ref="msg_2"/>
            </xsd:choice>
        </xsd:sequence>
        <xsd:attribute name="IdMsg" type="IdM" use="required"/>
    </xsd:complexType>
</xsd:element>

<xsd:group id="M39" name="msg_1">
    <xsd:sequence>
        <xsd:element name="anything" type="code"/>
        <xsd:element name="something_else" type="code"/>
   </xsd:sequence>
</xsd:group>
<xsd:group id="M40" name="msg_2">
    <xsd:sequence>
        <xsd:element name="nothing" type="code"/>
        <xsd:element name="something_else" type="code"/>
    </xsd:sequence>
</xsd:group>

<xsd:simpleType name="code">
    <xsd:restriction base="xsd:unsignedByte">
        <xsd:minInclusive value="0"/>
    </xsd:restriction>
</xsd:simpleType>

<xsd:simpleType name="IdM">
    <xsd:restriction base="xsd:unsignedByte">
        <xsd:minInclusive value="29"/>
        <xsd:maxInclusive value="42"/>
    </xsd:restriction>
</xsd:simpleType>


<xsd:group id="M2" name="header">
    <xsd:sequence>
        <xsd:element fixed="2" name="Version" type="xsd:unsignedInt"/>
        <xsd:element name="Timer" type="xsd:unsignedLong"/>
    </xsd:sequence>
</xsd:group>

Любопытно, что он работает даже с двумя элементами с одинаковыми именами (something_else). Если элементы с именами «что-нибудь» и «ничего» извлечены из msg_1 и msg_2, возникает проблема неоднозначности. Есть ли какое-либо объяснение по этому поводу? Я не вижу причин для такого поведения, поэтому я должен что-то упустить.

PS: Код здесь только пример, и я знаю, что две группы абсолютно одинаковы. Я сделал код, чтобы проиллюстрировать проблему. В моем приложении группы разные, хотя они имеют некоторые общие элементы.

1 Ответ

0 голосов
/ 20 февраля 2020

XSD разработан таким образом, что, когда валидатор встречает определенный элемент, валидатор без двусмысленности знает, где найти правила для этого элемента, основываясь только на его имени (и типе содержащего элемента). Ваша схема явно нарушает это правило: когда встречается Code, есть два возможных определения, и оно не будет знать, какое из них выбрать.

Если вы пытаетесь написать XSD для существующего класса из XML документов, в которых правила являются контекстно-зависимыми, тогда вы можете express использовать ограничения другим способом, например, используя утверждения XSD 1.1 или Schematron.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...