XSD Ejemplos


En esta sección se le mostrará cómo escribir un XML Schema. También aprenderá los diferentes métodos para escribir un schema.


Documento XML

Veamos el documento XML llamado "shiporder.xml":

<?xml version="1.0" encoding="ISO-8859-1"?>

<shiporder orderid="889923"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:noNamespaceSchemaLocation="shiporder.xsd">
  <orderperson>John Smith</orderperson>
  <shipto>
    <name>Ola Nordmann</name>
    <address>Langgt 23</address>
    <city>4000 Stavanger</city>
    <country>Norway</country>
  </shipto>
  <item>
    <title>Empire Burlesque</title>
    <note>Special Edition</note>
    <quantity>1</quantity>
    <price>10.90</price>
  </item>
  <item>
    <title>Hide your heart</title>
    <quantity>1</quantity>
    <price>9.90</price>
  </item>
</shiporder>

El documento XML anterior incluye el elemento raíz "shiporder", que contiene un atributo que debe llamarse "orderid". El elemento "shiporder" contiene tres elementos secundarios diferentes: "orderperson", "shipto" e "item". El elemento "item" aparece dos veces y contiene un "title", un elemento "note" opcional, un "quantity" y un "price".

La línea anterior xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" le dice al analizador XML que valide este documento contra un schema. Esta línea: xsi:noNamespaceSchemaLocation="shiporder.xsd" especifica la ubicación del schema (aquí, está en la misma carpeta que "shiporder.xml").


Crear un XML Schema

Ahora necesitamos crear un schema para el documento XML anterior.

Podemos comenzar abriendo un nuevo archivo y llamándolo "shiporder.xsd". Para crear el schema, simplemente necesitamos seguir la estructura del documento XML y definir cada elemento que encontremos. Primero comenzamos definiendo una declaración XML estándar:

<?xml version="1.0" encoding="ISO-8859-1" ?>
<xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema">
...
</xs:schema>

En el schema anterior, usamos el espacio de nombres estándar (xs). La URI asociada con este espacio de nombres es la definición del lenguaje del Schema (Schema language definition), cuyo valor estándar es http://www.w3.org/2001/XMLSchema.

A continuación, necesitamos definir el elemento "shiporder". Este elemento tiene un atributo y contiene otros elementos, por lo que lo identificamos como un tipo complejo. Los elementos secundarios del elemento "shiporder" están rodeados por el elemento xs:sequence, que define el orden de los elementos secundarios:

<xs:element name="shiporder">
  <xs:complexType>
    <xs:sequence>
      ...
    </xs:sequence>
  </xs:complexType>
</xs:element>

Luego necesitamos definir el elemento "orderperson" como un tipo simple (porque no contiene atributos ni otros elementos). El prefijo del tipo (xs:string) está determinado por el prefijo del espacio de nombres asociado al schema XML que designa los tipos de datos predefinidos del schema:

<xs:element name="orderperson" type="xs:string"/>

A continuación, debemos definir dos elementos como tipos complejos: "shipto" e "item". Comenzamos definiendo el elemento "shipto":

<xs:element name="shipto">
  <xs:complexType>
    <xs:sequence>
      <xs:element name="name" type="xs:string"/>
      <xs:element name="address" type="xs:string"/>
      <xs:element name="city" type="xs:string"/>
      <xs:element name="country" type="xs:string"/>
    </xs:sequence>
  </xs:complexType>
</xs:element>

En el schema, podemos usar los atributos maxOccurs y minOccurs para definir cuántas veces puede aparecer un elemento. maxOccurs define el número máximo de veces que puede aparecer un elemento, mientras que minOccurs define el número mínimo de veces que puede aparecer. ¡Los valores predeterminados de maxOccurs y minOccurs son 1!

Ahora podemos definir el elemento "item". Este elemento puede aparecer varias veces dentro del elemento "shiporder". Esto se logra estableciendo el valor del atributo maxOccurs del elemento "item" en "unbounded", de modo que el elemento "item" pueda aparecer tantas veces como el creador desee. Tenga en cuenta que el elemento "note" es opcional. Ya hemos establecido su atributo minOccurs en 0:

<xs:element name="item" maxOccurs="unbounded">
  <xs:complexType>
    <xs:sequence>
      <xs:element name="title" type="xs:string"/>
      <xs:element name="note" type="xs:string" minOccurs="0"/>
      <xs:element name="quantity" type="xs:positiveInteger"/>
      <xs:element name="price" type="xs:decimal"/>
    </xs:sequence>
  </xs:complexType>
</xs:element>

Ahora podemos declarar el atributo del elemento "shiporder". Como es un atributo obligatorio, especificamos use="required".

Nota:La declaración de este atributo debe colocarse al final:

<xs:attribute name="orderid" type="xs:string" use="required"/>

Este es el listado del archivo de schema llamado "shiporder.xsd":

<?xml version="1.0" encoding="ISO-8859-1" ?>
<xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema">

<xs:element name="shiporder">
  <xs:complexType>
    <xs:sequence>
      <xs:element name="orderperson" type="xs:string"/>
      <xs:element name="shipto">
        <xs:complexType>
          <xs:sequence>
            <xs:element name="name" type="xs:string"/>
            <xs:element name="address" type="xs:string"/>
            <xs:element name="city" type="xs:string"/>
            <xs:element name="country" type="xs:string"/>
          </xs:sequence>
        </xs:complexType>
      </xs:element>
      <xs:element name="item" maxOccurs="unbounded">
        <xs:complexType>
          <xs:sequence>
            <xs:element name="title" type="xs:string"/>
            <xs:element name="note" type="xs:string" minOccurs="0"/>
            <xs:element name="quantity" type="xs:positiveInteger"/>
            <xs:element name="price" type="xs:decimal"/>
          </xs:sequence>
        </xs:complexType>
      </xs:element>
    </xs:sequence>
    <xs:attribute name="orderid" type="xs:string" use="required"/>
  </xs:complexType>
</xs:element>

</xs:schema>


Dividir el Schema

El método de diseño anterior es muy fácil, pero resulta difícil de leer y mantener cuando el documento es complejo.

El siguiente método de diseño se basa en definir primero todos los elementos y atributos, y luego hacer referencia a ellos mediante el atributo ref.

Este es el archivo de schema diseñado con el nuevo método ("shiporder.xsd"):

<?xml version="1.0" encoding="ISO-8859-1" ?>
<xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema">

<!-- definition of simple elements -->
<xs:element name="orderperson" type="xs:string"/>
<xs:element name="name" type="xs:string"/>
<xs:element name="address" type="xs:string"/>
<xs:element name="city" type="xs:string"/>
<xs:element name="country" type="xs:string"/>
<xs:element name="title" type="xs:string"/>
<xs:element name="note" type="xs:string"/>
<xs:element name="quantity" type="xs:positiveInteger"/>
<xs:element name="price" type="xs:decimal"/>

<!-- definition of attributes -->
<xs:attribute name="orderid" type="xs:string"/>

<!-- definition of complex elements -->
<xs:element name="shipto">
  <xs:complexType>
    <xs:sequence>
      <xs:element ref="name"/>
      <xs:element ref="address"/>
      <xs:element ref="city"/>
      <xs:element ref="country"/>
    </xs:sequence>
  </xs:complexType>
</xs:element>

<xs:element name="item">
  <xs:complexType>
    <xs:sequence>
      <xs:element ref="title"/>
      <xs:element ref="note" minOccurs="0"/>
      <xs:element ref="quantity"/>
      <xs:element ref="price"/>
    </xs:sequence>
  </xs:complexType>
</xs:element>

<xs:element name="shiporder">
  <xs:complexType>
    <xs:sequence>
      <xs:element ref="orderperson"/>
      <xs:element ref="shipto"/>
      <xs:element ref="item" maxOccurs="unbounded"/>
    </xs:sequence>
    <xs:attribute ref="orderid" use="required"/>
  </xs:complexType>
</xs:element>

</xs:schema>


Uso de tipos con nombre (Named Types)

El tercer método de diseño define clases o tipos, lo que nos permite reutilizar las definiciones de elementos. La forma concreta es: primero nombrar los elementos simples y complejos, y luego hacer referencia a ellos mediante el atributo type del elemento.

Este es el archivo de schema diseñado con el tercer método ("shiporder.xsd"):

<?xml version="1.0" encoding="ISO-8859-1" ?>
<xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema">

<xs:simpleType name="stringtype">
  <xs:restriction base="xs:string"/>
</xs:simpleType>

<xs:simpleType name="inttype">
  <xs:restriction base="xs:positiveInteger"/>
</xs:simpleType>

<xs:simpleType name="dectype">
  <xs:restriction base="xs:decimal"/>
</xs:simpleType>

<xs:simpleType name="orderidtype">
  <xs:restriction base="xs:string">
    <xs:pattern value="[0-9]{6}"/>
  </xs:restriction>
</xs:simpleType>

<xs:complexType name="shiptotype">
  <xs:sequence>
    <xs:element name="name" type="stringtype"/>
    <xs:element name="address" type="stringtype"/>
    <xs:element name="city" type="stringtype"/>
    <xs:element name="country" type="stringtype"/>
  </xs:sequence>
</xs:complexType>

<xs:complexType name="itemtype">
  <xs:sequence>
    <xs:element name="title" type="stringtype"/>
    <xs:element name="note" type="stringtype" minOccurs="0"/>
    <xs:element name="quantity" type="inttype"/>
    <xs:element name="price" type="dectype"/>
  </xs:sequence>
</xs:complexType>

<xs:complexType name="shipordertype">
  <xs:sequence>
    <xs:element name="orderperson" type="stringtype"/>
    <xs:element name="shipto" type="shiptotype"/>
    <xs:element name="item" maxOccurs="unbounded" type="itemtype"/>
  </xs:sequence>
  <xs:attribute name="orderid" type="orderidtype" use="required"/>
</xs:complexType>

<xs:element name="shiporder" type="shipordertype"/>

</xs:schema>

El elemento restriction muestra que el tipo de datos se deriva de un tipo de datos del espacio de nombres W3C XML Schema. Por lo tanto, el siguiente fragmento significa que el valor de un elemento o atributo debe ser de tipo cadena:

<xs:restriction base="xs:string">

El elemento restriction se utiliza a menudo para imponer restricciones a los elementos. Vea los siguientes fragmentos del schema anterior:

<xs:simpleType name="orderidtype">
  <xs:restriction base="xs:string">
    <xs:pattern value="[0-9]{6}"/>
  </xs:restriction>
</xs:simpleType>

Este código indica que el valor del elemento o atributo debe ser una cadena, debe tener exactamente seis caracteres consecutivos, y estos caracteres deben ser dígitos del 0 al 9.

Otras extensiones