I am trying to define an XML Schema for a recursive data structure. Basically an element should be able to have children and properties, which is a list of elements that may in turn have children and properties. An "element" may be one of a range of type, all with the possibility of having children and properties in addition to some extra data. Thus, the element types are arranged in inherit from the BaseElementType
and add their own data on top.
I have made some progress but have run into an issue with with the validator accepting pretty much anything when moving down the structure.
My schema is as follows:
<?xml version="1.0" encoding="utf-8"?>
<xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema"
targetNamespace="http://www.example.org/ElementSchema" xmlns="http://www.example.org/ElementSchema">
<xs:element name="BaseElement" type="BaseElementType" />
<xs:element name="DoubleElement" type="DoubleElementType" />
<xs:element name="BoundedDoubleElement" type="BoundedDoubleElementType" />
<xs:element name="Properties" type="ElementList" />
<xs:element name="Children" type="ElementList" />
<xs:complexType name="ElementList">
<xs:choice minOccurs="1" maxOccurs="unbounded">
<xs:element name="BaseElement" />
<xs:element name="DoubleElement" />
<xs:element name="BoundedDoubleElement" />
</xs:choice>
</xs:complexType>
<xs:complexType name="BaseElementType">
<xs:sequence>
<xs:element name="Children" type="ElementList" minOccurs="0" />
<xs:element name="Properties" type="ElementList"
minOccurs="0" />
</xs:sequence>
<xs:attribute name="ID" type="xs:positiveInteger" use="required" />
<xs:attribute name="Key" type="xs:string" use="required" />
</xs:complexType>
<xs:complexType name="DoubleElementType">
<xs:complexContent>
<xs:extension base="BaseElementType">
<xs:sequence>
<xs:element name="Value" type="xs:float" />
</xs:sequence>
</xs:extension>
</xs:complexContent>
</xs:complexType>
<xs:complexType name="BoundedDoubleElementType">
<xs:complexContent>
<xs:extension base="DoubleElementType">
<xs:sequence>
<xs:element name="DesiredValue" type="xs:float" />
</xs:sequence>
</xs:extension>
</xs:complexContent>
</xs:complexType>
</xs:schema>
Here is an XML file that I am trying to validate. I have inserted the tags <wrongAccepted>
and <wrongRejected>
several places to demonstrate where the validation behaves as expected and where it accepts illegal tags.
<?xml version="1.0" encoding="utf-8"?>
<t:BoundedDoubleElement ID="12" Key="test"
xmlns:t="http://www.example.org/ElementSchema" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://www.example.org/ElementSchema ElementSchema.xsd">
<Children>
<BaseElement ID="13" Key="child">
<Properties>
<DoubleElement ID="10" Key="Null">
<Value>-INF</Value>
<wrongAccepted></wrongAccepted>
</DoubleElement>
<wrongAccepted></wrongAccepted>
</Properties>
</BaseElement>
<wrongRejected></wrongRejected>
</Children>
<Properties>
<wrongRejected></wrongRejected>
<DoubleElement ID="10" Key="Null" Role="LowerBound" Tag="-1">
<Value>-INF</Value>
<wrongAccepted></wrongAccepted>
</DoubleElement>
<DoubleElement ID="11" Key="Null" Role="UpperBound" Tag="-1">
<Value>INF</Value>
</DoubleElement>
</Properties>
<Value>10</Value>
<DesiredValue>10</DesiredValue>
<wrongRejected></wrongRejected>
</t:BoundedDoubleElement>
So how do I get it working such that it will reject the invalid tags?
Note: I am testing this in eclipse. I initially had some issues with getting it to validate at all, however it seems to be working now. Additionally the validator in Notepad++ yield exactly the same results.
Change
<xs:element name="DoubleElement" />
to
<xs:element name="DoubleElement" type="DoubleElementType"/>
Otherwise, you're effectively allowing DoubleElement
to allow any content because the default for xs:element/@type
(absent child simplyType
, child complexType
, and @substitutionGroup
attribute) is ur-type definition (anyType).
You probably want to do the same for the other children of ElementList
.