- From: Brenda Bell <bbell@juicesoftware.com>
- Date: Mon, 25 Feb 2002 13:58:54 -0500
- To: "'Jeni Tennison'" <jeni@jenitennison.com>, Brenda Bell <bbell@juicesoftware.com>
- Cc: "'xmlschema-dev@w3.org'" <xmlschema-dev@w3.org>
- Message-ID: <846B0B02E1B78B49B678EDCC00EB29627467C6@mail01.ent.juice.com>
Thank you so much for responding... and responding so quickly!!!
I actually found another option (perseverence is key :):
<xs:group name="baseGroup">
<xs:all>
<xs:element name="A" type="xs:string" minOccurs="1"
maxOccurs="1"/>
<xs:element name="B" type="xs:string" minOccurs="1"
maxOccurs="1"/>
<xs:element name="C" type="xs:string" minOccurs="1"
maxOccurs="1"/>
</xs:all>
</xs:group >
<xs:complexType name="extendedType">
<xs:sequence>
<xs:group ref="tns:baseGroup"/>
<xs:any namespace="##other" minOccurs="0"
maxOccurs="unbounded" processContents="skip"/>
</xs:sequence>
</xs:complexType>
<xs:element name="TOP" type="tns:extendedType"/>
</xs:schema>
Granted, my "extra" elements have to appear at the end but I do have
order-independence among my required elements. In retrospect, I think I'll
give extra consideration to your third scenario though...
-----Original Message-----
From: Jeni Tennison [mailto:jeni@jenitennison.com]
Sent: Monday, February 25, 2002 1:26 PM
To: Brenda Bell
Cc: 'xmlschema-dev@w3.org'
Subject: Re: Need help with any and all
Hi Brenda,
> I'm trying to develop a schema that requires element X to:
>
> have exactly one each of child elements A, B and C in any order
> allow other child elements from any other namespace
>
> I've been able to develop schemas that meet two of my three
> requirements but not all three. I've also been able to develop a
> schema that appears to meet all three, however validation succeeds
> when any of the required elements are omitted. If anyone else has
> done something similar, I would really appreciate any guidance you
> have to offer.
Yes, if you use xs:all to allow the elements to occur in any order
then you can't use the xs:any wildcard to allow any combination of
elements. If you use substitution groups, you can allow A, B or C in
any order, and use a wildcard, but you can't guarantee that there's
only one each of A, B and C.
So you have three options, I think:
Firstly, you could make the XML Schema enumerate the possible
combinations. This is a bit of a headache - not *too* awful with three
elements, but pretty bad:
<xs:sequence>
<xs:any namespace="##other" minOccurs="0" maxOccurs="unbounded" />
<xs:choice>
<xs:sequence>
<xs:element ref="A" />
<xs:any namespace="##other" minOccurs="0" maxOccurs="unbounded" />
<xs:choice>
<xs:sequence>
<xs:element ref="B" />
<xs:any namespace="##other" minOccurs="0" maxOccurs="unbounded"
/>
<xs:element ref="C" />
<xs:any namespace="##other" minOccurs="0" maxOccurs="unbounded"
/>
</xs:sequence>
<xs:sequence>
<xs:element ref="C" />
<xs:any namespace="##other" minOccurs="0" maxOccurs="unbounded"
/>
<xs:element ref="B" />
<xs:any namespace="##other" minOccurs="0" maxOccurs="unbounded"
/>
</xs:sequence>
</xs:choice>
</xs:sequence>
...
</xs:choice>
Secondly, you could use a more general content model, and then add any
additional constraints using a schema adjunct, such as Schematron. For
example:
<xs:choice minOccurs="3" maxOccurs="unbounded">
<xs:annotation>
<xs:appinfo>
<sch:rule context="X">
<sch:assert test="count(A) = 1">
There can only be one A element
</sch:assert>
<sch:assert test="count(B) = 1">
There can only be one B element
</sch:assert>
<sch:assert test="count(C) = 1">
There can only be one C element
</sch:assert>
</sch:rule>
</xs:appinfo>
</xs:annotation>
<xs:element ref="A" />
<xs:element ref="B" />
<xs:element ref="C" />
<xs:any namespace="##other" />
</xs:choice>
Thirdly, you could make your markup language easier to represent with
an XML Schema by wrapping the elements in other namespaces within
another element. Then you can use xs:all as follows:
<xs:all>
<xs:element ref="A" />
<xs:element ref="B" />
<xs:element ref="C" />
<xs:element name="D">
<xs:complexType>
<xs:sequence>
<xs:any namespace="##other" minOccurs="0"
maxOccurs="unbounded" />
</xs:sequence>
</xs:complexType>
</xs:element>
</xs:all>
Finally, you could make your markup language easier to represent with
an XML Schema by choosing a canonical representation in which the
order of A, B and C (and the wildcard) is specified. You could
constrain such a content model very easily:
<xs:sequence>
<xs:element ref="A" />
<xs:element ref="B" />
<xs:element ref="C" />
<xs:any namespace="##other" minOccurs="0" maxOccurs="unbounded" />
</xs:sequence>
You could provide a small script, stylesheet or query to transform
from unordered versions to the canonical ordering for the purpose of
validation.
Cheers,
Jeni
---
Jeni Tennison
http://www.jenitennison.com/
Received on Monday, 25 February 2002 13:59:27 UTC