XML Schema, abgekürztXSD(XML Schema Definition), ist eine Empfehlung desW3C zum Definieren von Strukturen fürXML-Dokumente. Anders als bei den klassischenXML-DTDs wird die Struktur in Form eines XML-Dokuments beschrieben. Darüber hinaus wird eine große Anzahl vonDatentypen unterstützt.
XML Schema beschreibt in einer komplexenSchemasprache Datentypen, einzelne XML-Schema-Instanzen (Dokumente) und Gruppen solcher Instanzen. Ein konkretes XML-Schema wird auch als eineXSD(XML Schema Definition) bezeichnet und hat als Datei üblicherweise dieEndung.xsd. Im Gegensatz zuDTDs kann bei Verwendung von XML-Schemata zwischen dem Namen des XML-Typs und dem in der Instanz verwendeten Namen des XML-Tags unterschieden werden.
NebenXML Schema gibt es weitere Konzepte zur Definition von XML-Strukturen, wieRELAX NG oderSchematron. AuchDTD als Normbestandteil von XML selbst kann verwendet werden.
XML Schema unterscheidet zwischen einfachen (atomaren) Datentypen und komplexen Datentypen. Der BegriffTyp bezeichnet im nachfolgenden Text jeweils die abstrakte Spezifikation der Struktur eines Abschnitts innerhalb eines XML-Dokumentes. Datentypen inXML Schema werden klassifiziert in eingebaute bzw. vordefinierte(built-in) und benutzerdefinierte(user defined) Datentypen.
In der Spezifikation des W3C fürXML Schema sind 19 voreingestellte primitive Datentypen (z. B.boolean, string, float, date undNOTATION) und weitere 25 davon abgeleitete primitive Datentypen (wieID undinteger) definiert.
XML Schema stellt einige grundlegende atomare Datentypen bereit. Die atomaren Datentypen enthalten die „klassischen“ Typen, wie sie zum Teil auch in anderen Typsystemen (z. B.C,Java oderSQL) spezifiziert sind:
xs:stringxs:decimalxs:integerxs:floatxs:booleanxs:datexs:timeHinzu kommen weitere XML-spezifische atomare Typen, unter anderem:
QName: qualifizierter Name, global eindeutiger Bezeichner. Aufgebaut aus sogenanntenNCNames (Non-Colonized Names), wobei jederNCName bis auf den letzten einenNamensraum(Namespace) bezeichnet. Der letzteNCName entspricht dem lokalen Namen innerhalb des Namensraumes. Die einzelnenNCNames werden mittels Punkt (.) zu einemQName zusammengesetzt.anyURI:Uniform Resource Identifier (URI)language: Sprachbezeichnung, z. B. de-DE, en-US, frID: Identifikationsattribut innerhalb von XML-ElementenIDREF: Referenz auf einen ID-WertEinfache XML-Datentypen dürfen weder XML-Kindelemente enthalten noch XML-Attribute besitzen.
Außer den atomaren Datentypen gehören Listen und Unions (bestehend aus atomaren Elementen und Listen) zu den einfachen Typen:
monatInt sowie eine Listemonate dieses neuen Typs:<xs:simpleTypename="monatInt"><xs:restrictionbase="xs:integer"><xs:minInclusivevalue="1"/><xs:maxInclusivevalue="12"/></xs:restriction></xs:simpleType><xs:simpleTypename="monate"><xs:listitemType="monatInt"/></xs:simpleType>
Eine Instanz des neuen Typs könnte wie folgt aussehen:
<monate>123456789101112</monate>
Die einzelnen Elemente einer Liste werden durchLeerraum (hier: Leerzeichen) getrennt.
Ein neuer Typ wird als Vereinigungsmenge bereits bestehender Typen definiert. Jede Instanz wählt dann ihren Typ aus dieser Menge.Das nachfolgende Beispiel definiert einen weiteren Typmonatsname sowie einen Union-Typmonat:
<xs:simpleTypename="monatsname"><xs:restrictionbase="xs:string"><xs:enumerationvalue="Jan"/><xs:enumerationvalue="Feb"/><xs:enumerationvalue="Mär"/><!-- und so weiter … --></xs:restriction></xs:simpleType><xs:simpleTypename="monat"><xs:unionmemberTypes="monatsname monatInt"/></xs:simpleType>
XML-Elemente vom Typmonat dürfen entweder ganzzahlige Werte im Bereich 1–12 enthalten oder eine der entsprechenden Monatsbezeichnungen alsZeichenkette. Gültige Instanzen sind beispielsweise:
<monat>Jan</monat><monat>2</monat>
In Ergänzung zu den einfachen Typen bieten komplexe XML-Datentypdefinitionen die Möglichkeit, Elementenstrukturen zusammenhängend zu definieren. Solche Strukturen können weitere Elemente und Attribute beinhalten.
Das folgende Beispiel definiert einen neuen Typpc-Typ mit entsprechenden Kindelementenname,hersteller etc., sowie einem Attributid:
<xs:complexTypename="pc-Typ"><xs:sequence><xs:elementname="name"type="xs:string"/><xs:elementname="hersteller"type="xs:string"/><xs:elementname="prozessor"type="xs:string"/><xs:elementname="mhz"type="xs:integer"minOccurs="0"/><xs:elementname="kommentar"type="xs:string"minOccurs="0"maxOccurs="unbounded"/></xs:sequence><xs:attributename="id"type="xs:integer"/></xs:complexType>
Die Möglichkeiten zur Definition komplexer Typen sollen hier nur exemplarisch erläutert werden. Der interessierte Leser sei auf die unten angegebenen Links zu den Seiten des W3C verwiesen.
Die Kindelemente eines komplexen Typs können auf drei unterschiedliche Arten kombiniert werden:
xs:sequence: Eine Liste von Kindelementen wird spezifiziert. Jedes dieser Elemente kann keinmal, einmal oder mehrfach auftreten (AttributeminOccurs undmaxOccurs). Falls keinoccurs-Attribut vorhanden ist, wird in beiden Fällen der Default-Wert 1 verwendet. Die Elemente innerhalb einersequence müssen in der angegebenen Reihenfolge auftreten. In dem oben gezeigten Beispiel müssen die Elementename,hersteller undprozessor genau einmal auftreten, dasmhz-Element kann null- oder einmal auftreten,kommentar-Elemente können beliebig oft oder auch gar nicht auftreten.xs:choice: Aus einer Liste von Alternativen kann ein Element ausgewählt werden. Das nachfolgende Beispiel definiert einen neuen Typcomputer, der als Kindelement entweder eindesktop-Element besitzt (vom Typpc-Typ) oder einlaptop-Element:<xs:complexTypename="computer"><xs:choice><xs:elementname="desktop"type="pc-Typ"/><xs:elementname="laptop"type="laptop-Typ"/></xs:choice></xs:complexType>
xs:all: Mittels desxs:all-Tags lässt sich eine Gruppe von Kindelementen definieren, von denen jedes maximal einmal auftreten darf (min- undmaxOccurs der Kindelemente dürfen nur die Werte 0 oder 1 annehmen). Die Reihenfolge der Elemente ist beliebig.XML-Elemente mit beliebigem Inhalt lassen sich mittels des BasistypsanyType definieren. Der nachfolgende Code spezifiziert einkommentar-Element beliebigen Inhalts, d. h. sowohl komplexe XML-Elemente als auch Text können vorkommen.
<xs:elementname="kommentar"type="xs:anyType"/>
Sollen in dem Inhalt Text und Tags in beliebiger Reihenfolge vorkommen können, muss der Wert für das Attribut "mixed" auf "true" gesetzt werden:
<xs:elementname="tagname"><xs:complexTypemixed="true"><xs:sequence><xs:elementminOccurs="0"maxOccurs="unbounded"name="child"type="xs:integer"/><!-- Weitere Elemente … --></xs:sequence></xs:complexType></xs:element>
Vonleeren XML-Elementen spricht man, wenn das jeweilige Element aus nur einem einzelnen XML-Tag besteht und keine weiteren XML-Elemente oder Text umschließt (z. B. der XHTML-Zeilenumbruch:<br />).XML Schema bedient sich an dieser Stelle eines kleinen Tricks: Es wird mittelsxs:complexType ein neuer Typ definiert, ohne ein Kindelement anzugeben. Daxs:complexType nach Vorgabe nur komplexe XML-Kindelemente als Inhalt zulässt, bleibt das jeweilige Element in diesem Fall leer.
Neue Datentypen lassen sich zum einen durch die Definition eines neuen Typs erstellen (siehe vorheriger Abschnitt) oder durch die Ableitung eines neuen Typs aus bereits bestehenden.
Bei der Ableitung eines neuen Typs handelt es sich nicht um eineVererbung im Sinne derObjektorientierung, da keine Eigenschaften vergleichbar den Methoden oder Attribute objektorientierterKlassen vererbt werden. Vielmehr handelt es sich hier um die Wiederverwendung bestehender Typdefinitionen. Dementsprechend ist bei der Ableitung neuer Typen auch keine implizite Substituierbarkeit gegeben, wie sie in anderen Typsystemen üblich ist (expliziteTypumwandlungen sind jedoch möglich).
DieAbleitung eines neuen Typs kann auf zweierlei Arten erfolgen: Erweiterung oder Einschränkung.
Die Erweiterung eines bisherigen Typs (engl.extension) um weitere Eigenschaften, d. h. neue Elemente oder Attribute werden hinzugefügt.Im folgenden Beispiel wird der oben definierte Typpc-Typ um ein Elementram erweitert:
<xs:complexTypename="myPC-Typ"><xs:complexContent><xs:extensionbase="pc-Typ"><xs:sequence><xs:elementname="ram"type="xs:integer"/></xs:sequence></xs:extension></xs:complexContent></xs:complexType>
Der neu definierte XML-TypmyPC-Typ besteht aus allen Kindelementen des Typspc-Typ sowie dem Elementram. Letzteres wird, wie in einerxs:sequence-Definition, an die bisherigen Kindelemente angehängt.
Da keine Substituierbarkeit gegeben ist, darf an einer Stelle an der ein Element vom Typpc-Typ erwartet wird nicht ohne weiteres ein Element vom TypmyPC-Typ verwendet werden.
Durch Einschränkung bereits bestehender Typen (engl.restriction) lassen sich ebenfalls neue Definitionen ableiten. Zu diesem Zweck müssen alle Elementdefinitionen des Basistyps wiederholt werden, verändert um die jeweiligen restriktiveren Einschränkungen. Im folgenden Beispiel wird ein neuer TypmyPC2-Typ vonpc-Typ abgeleitet. In diesem Fall darf maximal einkommentar-Element auftreten (im Gegensatz zu einer beliebigen Anzahl beim Typpc-Typ)
<xs:complexTypename="myPC2-Typ"><xs:complexContent><xs:restrictionbase="pc-Typ"><xs:sequence><xs:elementname="name"type="xs:string"/><xs:elementname="hersteller"type="xs:string"/><xs:elementname="prozessor"type="xs:string"/><xs:elementname="mhz"type="xs:integer"minOccurs="0"/><xs:elementname="kommentar"type="xs:string"minOccurs="0"maxOccurs="1"/></xs:sequence></xs:restriction></xs:complexContent></xs:complexType>
Zusätzlich zu der Einschränkung komplexer Typen ist es auch möglich, neue Typen als Einschränkung einfacher Typen zu definieren. Ein Beispiel für eine solche Definition befindet sich bereits im Abschnitt zu den einfachen Typen. Ein neuer TypmonatInt wird als Einschränkung des Typs Integer auf den Wertebereich 1–12 definiert. Grundsätzlich stehen die folgenden Primitive zur Verfügung, um Einschränkungen auf einfachen Typen zu beschreiben:
length,maxLength,minLength – Beschränkt die Länge eines Strings oder einer Liste.enumeration – Beschränkung durch Angabe alternativer Wertepattern – Beschränkung durch Angabe einesregulären AusdrucksminExclusive,minInclusive,maxExclusive,maxInclusive – Einschränkung des Wertebereichs.totalDigits,fractionDigits – Einschränkung der Dezimalstellen (Gesamtzahl und Nachkommastellen)whiteSpace – Behandlung von Leerzeichen und TabsDie folgenden Beispiele veranschaulichen die Verwendung dieser Komponenten:
<xs:simpleTypename="celsiusKörperTemp"><xs:restrictionbase="xs:decimal"><xs:totalDigitsvalue="3"/><xs:fractionDigitsvalue="1"/><xs:minInclusivevalue="35.0"/><xs:maxInclusivevalue="42.5"/></xs:restriction></xs:simpleType>
D“ gefolgt von fünf Ziffern<xs:simpleTypename="plz"><xs:restrictionbase="xs:string"><xs:patternvalue="(D )?[0-9]{5}"/></xs:restriction></xs:simpleType>
<xs:simpleTypename="size"><xs:restrictionbase="xs:string"><xs:enumerationvalue="XS"/><xs:enumerationvalue="S"/><xs:enumerationvalue="M"/><xs:enumerationvalue="L"/><xs:enumerationvalue="XL"/></xs:restriction></xs:simpleType>
Bei der Definition eines Typs ist es möglich festzulegen, ob und auf welche Art von diesem Typ weitere XML-Elementtypen abgeleitet werden dürfen. So kann man zum Beispiel festlegen, dass von einem Typpc-Typ weitere Typen nur durch das Setzen weiterer Einschränkungen abgeleitet werden dürfen – und nicht durch das Hinzufügen neuer Kindelemente.
Wie im vorangegangenen Abschnitt erläutert erlaubt esXML Schema, neue XML-Datentypen zu definieren und diese bei der Definition eigener XML-Elemente zu verwenden. Das folgende Beispiel veranschaulicht die Verwendung des bereits definierten Typspc-Typ innerhalb einer Liste von pc-Elementen:
<xs:elementname="pc-liste"><xs:complexType><xs:sequence><xs:elementname="pc"type="pc-Typ"maxOccurs="unbounded"/></xs:sequence></xs:complexType></xs:element>
Ein entsprechendes XML-Element könnte wie folgt aussehen:
<pc-liste><pc><name>Dimension3100</name><hersteller>Dell</hersteller><prozessor>AMD</prozessor><mhz>3060</mhz><kommentar>Arbeitsplatzrechner</kommentar></pc><pc><name>T42</name><hersteller>IBM</hersteller><prozessor>Intel</prozessor><mhz>1600</mhz><kommentar>Laptop</kommentar></pc></pc-liste>
In diesem Beispiel erfolgt die Spezifikation desanonymen Listentyps direkt innerhalb der Elementdefinition, während die Spezifikation des pc-Typs extern erfolgt.
Bei dem Entwurf eines komplexen XML-Schemas sollte sowohl dieWiederverwendbarkeit und Erweiterbarkeit der einzelnen XML-Elementtypen als auch die Lesbarkeit des Schemas selbst berücksichtigt werden. Die Verwendung anonymer XML-Elementtypen als Teil größerer Elemente gewährleistet im Allgemeinen eine bessere Lesbarkeit kleinerer XML-Schemata. Die Definition und Benennung einzelner, kleinerer und wiederverwendbarer XML-Elementtypen hingegen ermöglicht eine stärkere Modularisierung der XML-Schema-Struktur. Aufgrund der Vielzahl möglicher Anwendungsszenarien haben sich bisher noch keine allgemeingültigen Entwurfsprinzipien für XML-Schemata herausgebildet (vergleichbar denNormalformen für relationale Datenbanken).
Vergleichbar denPrimärschlüsseln inrelationalen Datenbanken lassen sich mittelsXML Schema eindeutige Schlüssel definieren.XML Schema unterscheidet zwischen der Eindeutigkeit (engl.unique) und der Schlüsseleigenschaft.
Das nachfolgende Beispiel definiert ein neues Elementpc-list mit einer Liste vonpc-Kindelementen:
<xs:elementname="pc-list"><xs:complexType><xs:sequence><xs:elementname="pc"type="pc-Typ"maxOccurs="unbounded"/></xs:sequence></xs:complexType><xs:uniquename="hersteller-name"><xs:selectorxpath="pc"/><xs:fieldxpath="name"/><xs:fieldxpath="hersteller"/></xs:unique><xs:keyname="idKey"><xs:selectorxpath="pc"/><xs:fieldxpath="@id"/></xs:key></xs:element>
Die beiden Elementeunique undkey selektieren mit einemXPath Pfadausdruck (im Beispiel:pc) eine Menge vonpc-Elementen. Für diese Menge muss die jeweilige Eindeutigkeits- bzw. Schlüsselbedingung erfüllt werden.Im obigen Beispiel wird festgelegt, dass die Kombination der Elementename undhersteller für jedespc-Element innerhalb dieser Liste eindeutig sein muss.
Durch daskey-Element wird festgelegt, dass das Attributid innerhalb dieser Liste eindeutig sein muss und von außerhalb referenziert werden kann.
Das folgende Beispiel zeigt die Referenzierung dieses Schlüssels mit dem Attributrefer und dem Schlüsselwort@references.
<xs:keyrefname="idFremdKey"refer="idKey"><!-- idKey von obigem Beispiel --><xs:selectorxpath="computerFremd"/><xs:fieldxpath="@references"/></xs:keyref>
Mitrefer bezieht man sich auf dasname-Attribut einer Schlüsselbedingung, nicht auf das Schlüsselfeld. Die Werte inreferences müssen also immer unter den Schlüsseln zu dencomputern zu finden sein. (Hintergrund dieses Konstrukts ist die Sicherstellung derreferentiellen Integrität, wie man sie von relationalen Datenbanksystemen her kennt.)
XML Schema erlaubt es, fremde Schemata wiederzuverwenden.
Hierzu stehen sowohl derinclude- als auch derimport-Tag zur Verfügung sowie die Möglichkeit einer neuen Definition bzw. Anpassung fremder Schemata beim Einbinden.
includeTypdefinitionen innerhalb eines Namensraumes, die auf mehrere Dateien verteilt sind, lassen sich mittelsinclude zusammenfügen.
<schemaxmlns="http://www.w3.org/2001/XMLSchema"xmlns:pcTeile="http://www.example.com/pcTeile"targetNamespace="http://www.example.com/pcTeile">…<includeschemaLocation="http://www.example.com/schemata/harddisk.xsd"/><includeschemaLocation="http://www.example.com/schemata/ram.xsd"/>…</schema>
targetNamespace desharddisk.xsd muss mit dem des inkludierenden Schemas übereinstimmen.redefineGleiches Beispiel wie gerade. Annahme es gäbe einencomplexTypeHersteller im Schemaharddisk.xsd.
<schemaxmlns="http://www.w3.org/2001/XMLSchema"xmlns:pcTeile="http://www.example.com/pcTeile"targetNamespace="http://www.example.com/pcTeile">…<redefineschemaLocation="http://www.example.com/schemata/harddisk.xsd"><!-- redefinition of Hersteller --><complexTypename="Hersteller"><complexContent><!-- redefinition of Hersteller mit ''restriction'' oder auch ''extension'' etc. --><restrictionbase="pcTeile:Hersteller"><sequence><elementname="hersteller"type="string"minOccurs="10"maxOccurs="10"/></sequence></restriction></complexContent></complexType></redefine>…<includeschemaLocation="http://www.example.com/schemata/ram.xsd"/>…</schema>
redefine kann an Stelle voninclude verwendet werden.importDerimport-Tag erlaubt es, Elemente aus anderen Namensräumen zu importieren, mit einem Präfix zu versehen unddamit Schema-Bestandteile aus unterschiedlichen Namensräumen wiederzuverwenden.
Annahme ist, dass es einen definierten TypsuperTyp inpcTeile gibt.
<schemaxmlns="http://www.w3.org/2001/XMLSchema"xmlns:pcTeile="http://www.example.com/pcTeile"targetNamespace="http://www.example.com/firma">…<importnamespace="http://www.example.com/pcTeile"/>…<…<xs:attributename="xyz"type="pcTeile:superTyp"/>…/>…</schema>
Zur Verwendung eines XML-Schemas in einer XML-Datei kann das AttributschemaLocation des Schema-Instance-Namensraums verwendet werden, um die Adresse des Schemas bekannt zu machen.Somit ist es einer Anwendung wie beispielsweise einem XML-Parser möglich, das Schema zu laden, sofern es ihm nicht schon bekannt ist. Alternativ kann der Anwendung das Schema aber auch über andere Wege bekannt gemacht werden, z. B. über Konfigurationsdateien. Letztere Möglichkeit ist jedoch nicht standardisiert und somit von Anwendung zu Anwendung verschieden.
In folgendem Beispiel wird ausgedrückt, dass der Standard-Namensraumhttp://www.w3.org/1999/xhtml ist und dann angegeben, dass das XML-Schema für diesen Namensraum unterwww.w3.org/1999/xhtml.xsd[1] aufzufinden ist.
<htmlxmlns="http://www.w3.org/1999/xhtml"xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"xsi:schemaLocation="http://www.w3.org/1999/xhtml http://www.w3.org/1999/xhtml.xsd">
Die Definition gilt für das XML-Element, bei dem die Attribute angegeben sind, und alle Kinderelemente.
Soll Elementen, die keinem Namensraum angehören, ein XML-Schema zugeordnet werden, so geschieht dies, wie im folgenden Beispiel gezeigt, mittels des AttributesnoNamespaceSchemaLocation.
<htmlxmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"xsi:noNamespaceSchemaLocation="http://www.w3.org/1999/xhtml.xsd">
<?xml version="1.0" encoding="UTF-8"?><schemaxmlns="http://www.w3.org/2001/XMLSchema"xmlns:bsp="http://de.wikipedia.org/wiki/XML_Schema#Beispiel"targetNamespace="http://de.wikipedia.org/wiki/XML_Schema#Beispiel"elementFormDefault="qualified"><elementname="doc"><complexType><sequence><elementref="bsp:head"/><elementname="body"type="string"/></sequence></complexType></element><elementname="head"><complexType><sequence><elementname="title"type="string"/></sequence></complexType></element></schema>
Dies entspricht, abgesehen vom Namensraum, folgenderDTD
<!ELEMENT doc (head, body)><!ELEMENT head (title)><!ELEMENT title (#PCDATA)><!ELEMENT body (#PCDATA)>
Eine XML-Struktur, die dem Schema entspricht, ist diese:
<?xml version="1.0" encoding="UTF-8"?><docxmlns="http://de.wikipedia.org/wiki/XML_Schema#Beispiel"><head><title>DiesistderTitel</title></head><body>DiesistderText.</body></doc>