[
Lists Home |
Date Index |
Thread Index
]
Hi Martin,
> I have a question on defining occurences in choices within schema.
[snip]
> where testentry should be a base type which gets then restricted.
> The name element must have certain fixed values. Depending on some
> of these values I want to define occurences/restrictions (minOccurs,
> maxOccurs, etc.) for the whole element. How can I do that?
I'm not sure which thing you want to affect the occurrence of -- is it
the <content> elements? If so, this is known as a "co-occurrence
constraint" -- the value of an element is affecting the content model
that you want to use. I'm afraid that co-occurrence constraints aren't
well supported in W3C XML Schema. The closest that you can do is:
<?xml version="1.0" encoding="UTF-8"?>
<xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema"
elementFormDefault="qualified"
attributeFormDefault="unqualified">
<xs:element name="test">
<xs:complexType>
<xs:sequence>
<xs:element name="testentry" maxOccurs="unbounded">
<xs:complexType>
<xs:complexContent>
<xs:restriction base="testType">
<xs:element name="name">
<xs:simpleType>
<xs:restriction base="xs:string">
<xs:enumeration value="value1" />
<xs:enumeration value="value2" />
</xs:restriction>
</xs:simpleType>
</xs:element>
<xs:element name="content" type="xs:string"
minOccurs="0" maxOccurs="unbounded" />
</xs:restriction>
</xs:complexContent>
</xs:complexType>
</xs:element>
</xs:sequence>
</xs:complexType>
</xs:element>
<xs:complexType name="testType">
<xs:sequence>
<xs:element name="name" type="xs:string"/>
<xs:element name="content" type="xs:string"
minOccurs="0" maxOccurs="unbounded" />
</xs:sequence>
</xs:complexType>
</xs:schema>
You can then have an additional layer of constraints expressed using
Schematron rules. For example:
<sch:rule context="testentry[name = 'value1']">
<sch:assert test="content">
A testentry whose name element child is 'value1' must have at
least one content element child.
</sch:assert>
</sch:rule>
Or, of course, you could swap to RELAX NG, which supports this kind of
constraint very easily:
element test {
element testentry {
(element name { "value1" }, element content { text }+) |
(element name { "value2" }, element content { text }*)
}+
}
Cheers,
Jeni
---
Jeni Tennison
http://www.jenitennison.com/
|