LeTigre
LeTigre

Reputation: 460

Reference a XML type in a XML Schema

Given the following XML I want to reference the different exercises by their type:

<root>
    <exercises type="foo">
        <text></text>
    </exercises>
    <exercises type="bar">
        <audio></audio>
    </exercises>
</root>

I would set this up like that:

<?xml version="1.0"?>
<xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema">
<!-- xml def -->
<xs:element name="root">
<xs:complexType>
    <xs:sequence>
        <xs:element name="exercises" type="foo-exercises"/>
        <xs:element name="exercises" type="bar-exercises"/>
    </xs:sequence>
</xs:complexType>
</xs:element>

But how do I explicitly check for the "type" definition in the given xml? That is, that the elements are of the given type? That is, that the given types are checked against the corresponding definition?


Edit: I put it oddly: My problem is, to reference the "type" / attribute not in the type definition but in the reference to the fields.

Say: I want to check, whether there actually are 3 elements of type foo and 2 elements of type bar. So exercise is not descriptive enough...

Upvotes: 0

Views: 134

Answers (2)

potame
potame

Reputation: 7905

I'm afraid this kind of element definition can not be achieved with XML Schemas. In other words, you can not bound an element content model to a particular value of an attribute on this element (or in any other element).

Such control can be achieved with Schematron for example.

Upvotes: 2

Xstian
Xstian

Reputation: 8282

I suggest you this schema ..

<xs:schema attributeFormDefault="unqualified" elementFormDefault="qualified"
    xmlns:xs="http://www.w3.org/2001/XMLSchema">
    <xs:element name="root">
        <xs:complexType>
            <xs:sequence>
                <xs:element name="exercises" maxOccurs="unbounded" minOccurs="0" type="exercise"/>
            </xs:sequence>
        </xs:complexType>
    </xs:element>

    <xs:complexType name="exercise">
        <xs:sequence>
        </xs:sequence>
    </xs:complexType>

    <xs:complexType name="foo">
        <xs:complexContent>
            <xs:extension base="exercise">
                <xs:sequence>
                    <xs:element type="xs:string" name="text" minOccurs="0"/>
                </xs:sequence>
            </xs:extension>
        </xs:complexContent>
    </xs:complexType>

    <xs:complexType name="bar">
        <xs:complexContent>
            <xs:extension base="exercise">
                <xs:sequence>
                    <xs:element type="xs:string" name="audio" minOccurs="0"/>
                </xs:sequence>
            </xs:extension>
        </xs:complexContent>
    </xs:complexType>
</xs:schema>

this is the related xml...

<?xml version="1.0" encoding="UTF-8"?>
<root xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" >
    <exercises xsi:type="foo">
        <text></text>   
    </exercises>
    <exercises xsi:type="bar">
        <audio></audio> 
    </exercises>
</root>

In this way you used an xsd extension. See here the reference

Upvotes: 2

Related Questions