Concrete type definitions in multiple schemas
I have created a main schema (main.xsd) which includes an abstract element for extensibility by other users..
<!-- main.xsd -->
<?xml version="1.0" encoding="UTF-8"?>
<xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema" xmlns="urn:paul:main"
targetNamespace="urn:paul:main" elementFormDefault="qualified" attributeFormDefault="unqualified">
<xs:element name="Root">
<xs:complexType>
<xs:sequence>
<xs:element name="Extension" type="myAbstract" minOccurs="0" maxOccurs="unbounded"/>
</xs:sequence>
</xs:complexType>
</xs:element>
<xs:complexType name="myAbstract" abstract="true">
<xs:attribute name="extensionName" use="required">
<xs:simpleType>
<xs:restriction base="xs:string">
<xs:pattern value="[A-Za-z0-9]+"/>
</xs:restriction>
</xs:simpleType>
</xs:attribute>
</xs:complexType>
</xs:schema>
Now a colleague (Dave) creates an XML document (dave.xml) so he develops his own schema (ext1.xsd) to define a concrete type for
<!-- ext1.xsd -->
<?xml version="1.0" encoding="UTF-8"?>
<xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema" elementFormDefault="qualified"
attributeFormDefault="unqualified"
targetNamespace="urn:dave:ext" xmlns="urn:dave:ext" xmlns:main="urn:paul:main">
<xs:import namespace="urn:paul:main" schemaLocation="main.xsd"/>
<xs:complexType name="Daves-extn">
<xs:complexContent>
<xs:extension base="main:myAbstract">
<xs:sequence>
<xs:element name="extensionElement" type="xs:string"/>
</xs:sequence>
</xs:extension>
</xs:complexContent>
</xs:complexType>
</xs:schema>
<!-- dave.xml -->
<?xml version="1.0" encoding="UTF-8"?>
<Root xmlns="urn:paul:main" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:ext1="urn:dave:ext" xmlns:ext2="urn:john:ext"
xsi:schemaLocation="urn:paul:main ./main.xsd urn:dave:ext ./ext1.xsd">
<Extension xsi:type="ext1:Daves-extn" extensionName="DAVE001">
<ext1:extensionElement>An Extension</ext1:extensionElement>
</Extension>
</Root>
and his XML document validates using xmllint --schema ext1.xsd dave.xml
John also wants to add to so he defines something similar in ext2.xsd
<!-- john.xsd -->
<?xml version="1.0" encoding="UTF-8"?>
<xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema"
xmlns="urn:john:ext" xmlns:main="urn:paul:main"
targetNamespace="urn:john:ext" elementFormDefault="qualified" attributeFormDefault="unqualified">
<xs:import namespace="urn:paul:main" schemaLocation="main.xsd"/>
<xs:complexType name="Johns-extn">
<xs:complexContent>
<xs:extension base="main:myAbstract">
<xs:sequence>
<xs:element name="anInteger" type="xs:integer"/>
</xs:sequence>
</xs:extension>
</xs:complexContent>
</xs:complexType>
</xs:schema>
So far, this is all OK. Now Mike wants an XML document (Mike.xml) that uses the extensions defined by Dave and John so he develops the following
<!-- john.xml -->
<?xml version="1.0" encoding="UTF-8"?>
<Root xmlns="urn:paul:main" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:ext1="urn:dave:ext" xmlns:ext2="urn:john:ext"
xsi:schemaLocation="urn:paul:main ./main.xsd urn:dave:ext ./ext1.xsd urn:john:ext ./ext2.xsd">
<Extension xsi:type="ext1:Daves-extn" extensionName="DAVE001">
<ext1:extensionElement>An Extension</ext1:extensionElement>
</Extension>
<Extension xsi:type="ext2:Johns-extn" extensionName="JOHN001">
<ext2:anInteger>12</ext2:anInteger>
</Extension>
</Root>
This XML document requires both ext1.xsd and ext2.xsd to validate, and both xmllint --schema ext1.xsd john.xml
and xmllint --schema ext2.xsd john.xml
report an error with the element from the other extension.
Note that john.xml
does pass validation in XML Spy
In this case, both concrete types are derived from a single abstract type, but a valid main schema could use multiple abstract types for multiple elements - this would also require multiple schema files to be used in validation.
This is also reported as libxmljs2 issue 85 as I have been using the Javascript bindings to libxml