Основы использования XML-схем для определения элементов

Используйте для определения структуры XML-документов XML-схемы вместо DTD

Новая система использования XML-схем, теперь получившая подтверждение в качестве рекомендации W3C, обеспечивает для XML-документов богатую грамматическую структуру, которая преодолевает ограничения DTD (см. вставку Ограничения DTD). Данная статья демонстрирует гибкость схем и показывает, как определять наиболее фундаментальный конструктивный блок XML-документов – элемент – в системе XML-схемы.

Ashvin Radiya, Президент и Главный Технический Руководитель, AvantSoft, Inc.

Ashvin Radiya является основателем и президентом AvantSoft, Inc. В качестве Главного Технического Руководителя он возглавляет разработку и выпуск курсов тренинга AvantSoft по искусству програмирования на Java и родственным технологиям. Он создал и поддерживает стратегическое партнерство с компаниями Fortune 100. Ashvin обладает большим производственным, академическим и профессиональным опытом. Работал в представительстве IBM в Остине над продвинутыми распределенными объектно-ориентированными продуктами на основе CORBA. Обладает большими знаниями и опытом в областях мобильной коммерции, XML, Java, JavaBeans, компонентов Enterprise JavaBeans, InfoBus, Security, CORBA и распределенного ООП. Получил степень доктора в области компьютерных наук в университете г.Сиракузы, штат Нью Йорк. Связаться с ним можно по адресу ashvin@avantsoft.com.



Vibha Dixit, Исполнительный Директор, AvantSoft, Inc.

Vibha Dixit является Управляющим Бизнес-разработками и Технологом в AvantSoft, Inc. Она занимается планированим бизнеса, управлением стратегическими партнерствами, привлечением новых клиентов, продажами и маркетингом. Активно участвует в постановке для AvantSoft технических задач и направлений в областях мобильной коммерции, XML и Java-технологий. Vibha обладает уникальным опытом в управлении бизнесом и большим производственным опытом в компьютерных технологиях. Перед приходом в AvantSoft работала в лаборатории IBM в Santa Teresa над распределенным промежуточным ПО для осуществления транзакций. Участвовала в проектировании и разработке операционной системы для кластерных систем в центре Ohio Supercomputer Center. Получила степень доктора в области компьютерных наук в Университете штата Огайо. Закончила курсы MBA в Южном методистском университете. Связаться с ней можно по адресу vibha@avantsoft.com.



01.08.2000

XML-схема обладает более мощными возможностями, чем DTD. Для иллюстрации преимуществ использования механизма XML-схем в первых трех листингах сравниваются различные способы представления элементов. В Листинге 1 представлена выдержка из XML-документа. В Листинге 2 показаны два элемента, объявленные в синтаксисе DTD, а в Листинге 3 представлен синтаксис, соответствующий XML-схеме. Обратите внимание, что синтаксис в Листинге 3 подобен синтаксису XML. При использовании схемы, валидирующий парсер может выполнить проверку, является ли элемент InvoiceNo положительным целым числом, и состоит ли ProductID из заданного набора символов (шести цифр и одной буквы от A до Z). Парсер, обрабатывающий DTD-определение, может лишь подтвердить, что данные элементы представляют собой строки.

Листинг 1: Фрагмент XML-документа
<InvoiceNo>123456789</InvoiceNo>
<ProductID>J123456</ProductID>
Листинг 2: Фрагмент DTD, описывающий элементы из Листинга 1
<!ELEMENT InvoiceNo (#PCDATA)>
<!ELEMENT ProductID (#PCDATA)>
Листинг 3: Фрагмент XML-схемы, описывающий элементы из Листинга 1
<element name='InvoiceNo' type='positive-integer'/>
<element name='ProductID' type='ProductCode'/>
<simpleType name='ProductCode' base='string'>
  <pattern value='[A-Z]{1}d{6}'/>
</simpleType>

Использование пространств имен в XML-схеме

Ограничения DTD

Несмотря на то, что DTD служат разработчикам SGML и HTML в качестве механизма описания структурированной информации вот уже на протяжении 20-ти лет, DTD обладают некоторыми ограничениями по сравнению с XML-схемами.

Согласно DTD элемент может быть представлен одним из трех способов:

  • Текстовая строка
  • Текстовая строка, смешанная с другим дочерним элементом
  • Набор дочерних элементов

DTD не обладает синтаксисом XML и предлагает лишь ограниченную поддержку для типов и пространств имен.

При совместной работе одна сторона может обрабатывать документы других сторон, и разные стороны могут представлять свои элементы данных по-разному. Более того, в отдельном документе им может потребоваться независимо друг от друга ссылаться на элементы с одинаковым именем, созданные разными сторонами. Использование XML-схемы позволяет различать определения с одним и тем же именем при помощи определения разных пространств имен.

Такая XML-схема определяет набор новых имен, таких как имена элементов, типов, атрибутов, групп атрибутов, чьи определения и объявления описаны в схеме. В Листинге 3 имена определяются как InvoiceNo, ProductID и ProductCode.

Имена, определенные в схеме принадлежат так называемому целевому пространству имен. Само по себе пространство имен является фиксированным, произвольным именем, которое должно соответствовать синтаксису URL. К примеру, пространство имен для схемы, представленной в Листинге 3, можно задать следующим образом: http://www.SampleStore.com/Account.

Синтаксис объявления пространства имен иногда может сбить с толку. Объявление начинается с http://, однако оно не ссылается на файл с описанием схемы. На самом деле, ссылка http://www.SampleStore.com/Account вообще не ведет ни на один файл, а только на назначенное имя.

Определения и объявления в схеме могут ссылаться на имена, которые могут принадлежать другим пространствам имен. В данной статье мы ссылаемся на такие пространства имен как на исходные пространства имен. В каждой схеме может быть определено одно целевое пространство имен и возможно множество исходных пространств имен. Вообще, каждое имя в заданной схеме принадлежит некоему пространству имен. Имена пространства имен могут быть довольно длинными, однако их можно сократить при помощи синтаксиса объявления xmlns в документе XML-схемы. Все эти концепции проиллюстрированы в Листинге 4.

Листинг 4: Целевое и исходное пространства имен
<!--XML Schema fragment in file schema1.xsd-->

<xsd:schema targetNamespace='http://www.SampleStore.com/Account'
      xmlns:xsd='http://www.w3.org/1999/XMLSchema'
      xmlns:ACC= 'http://www.SampleStore.com/Account'>
<xsd:element name='InvoiceNo' type='xsd:positive-integer'/>
<xsd:element name='ProductID' type='ACC:ProductCode'/>
<xsd:simpleType name='ProductCode' base='xsd:string'>
  <xsd:pattern value='[A-Z]{1}d{6}'/>
</xsd:simpleType>

В XML-схеме, представленной с Листинге 4, пространством имен targetNamespace является http://www.SampleStore.com/Account, оно содержит имена InvoiceNo, ProductID и ProductCode. Имена schema, element, simpleType, pattern, string и positive-integer принадлежат исходному пространству имен http://www.w3.org/1999/XMLSchema, которое сокращается как xsd путем объявления xmlns. В псевдониме xsd нет ничего особенного, можно выбрать и другое имя. Для удобства и простоты в оставшейся части статьи мы будем использовать префикс xsd для ссылки на пространство имен http://www.w3.org/1999/XMLSchema, пропуская уточнение xsd в некоторых частях кода. В нашем примере targetNamespace является также одним из исходных пространств имен, так как имя ProductCode используется в определении других имен.

Рисунок 1: Пространства имен для Листинга 4
Пространства имен для Листинга 4

Во фрагменте схемы из Листинга 4 не нужно указывать расположение исходных файлов схемы. Для общей "схемы схем" http://www.w3.org/1999/XMLSchema указывать путь не нужно, так как он хорошо известен. Вам также не нужно указывать местоположение исходного пространства имен http://www.SampleStore.com/Account, так как оно выступает здесь также целевым пространством имен, определенным в данном файле. Для полного понимания определения местоположения схемы и использования пространства имен по умолчанию ознакомьтесь с дополнением к примеру в Листинге 5.

Листинг 5: Множество исходных пространств имен, импорт пространства имен
<!--XML Schema fragment in file schema1.xsd-->
<schema targetNamespace='http://www.SampleStore.com/Account'
      xmlns='http://www.w3.org/1999/XMLSchema'
      xmlns:ACC= 'http://www.SampleStore.com/Account'
      xmlns:PART= 'http://www.PartnerStore.com/PartsCatalog'>
<import namespace='http://www.PartnerStore.com/PartsCatalog'
        schemaLocation='http://www.ProductStandards.org/repository/alpha.xsd'/>
<element name='InvoiceNo' type='positive-integer'/>
<element name='ProductID' type='ACC:ProductCode'/>
<simpleType name='ProductCode' base='string'>
  <pattern value='[A-Z]{1}d{6}'/>
</simpleType>
<element name='stickyGlue' type='PART:SuperGlueType'/>

Листинг 5 включает еще одну ссылку на пространство имен - http://www.PartnerStore.com/PartsCatalog. Оно отличается от пространства targetNamespace и стандартных пространств имен. Поэтому его нужно импортировать при помощи тега import, чей атрибут schemaLocation задает местоположение файла, содержащего схему. Пространством имен по умолчанию является http://www.w3.org/1999/XMLSchema, чье объявление xmlns не имеет имени. Каждое неквалифицированное имя, такое как schema и element принадлежит пространству имен, заданному по умолчанию – http://www.w3.org/1999/XMLSchema. Если ваша схема ссылается на несколько имен из одного пространства, удобнее всего будет обозначить его как пространство имен по умолчанию.

XML-документ может ссылаться на имена элементов из множества пространств имен, определенных во множестве схем. Для обращения к пространствам имен используются объявления xmlns. Для задания расположения файлов используется атрибут schemaLocation из пространства имен XML Schema. Обратите внимание, что данный атрибут отличается от атрибута schemaLocation пространства имен xsd из предыдущих примеров.

Листинг 6: Использование множества пространства имен из множества схем
<?xml version="1.0"?>
<ACC:rootElement xmlns:ACC='http://www.SampleStore.com/Account'
      xmlns:PART='http://www.PartnerStore.com/PartsCatalog'
      xmlns:xsi='http://www.w3.org/1999/XMLSchema-instance'
      xsi:schemaLocation='http://www.PartnerStore.com/PartsCatalog
                          http://www.ProductStandards.org/repository/alpha.xsd
                          http://www.SampleStore.com/Account
                          http://www.SampleStore.com/repository/schema1.xsd'>
<ACC:InvoiceNo>123456789</ACC:InvoiceNo>
Рисунок 2: Пространства имен для Листингов 5 и 6
Пространства имен для Листингов 5 и 6

Определение элементов

Определением элемента заключается в определении его имени и модели контента. В XML-схеме модель контента элемента определяется его типом. Следовательно, элементы в XML-документе могут иметь только значения, которые подходят типам, определенным в его схеме.

Простые типы

Спецификация XML-схемы определяет несколько простых типов для значений, как показано в Таблице 2 -предопределенные простые типы значений.

Тип элемента может быть простым или комплексным (сложным). Элемент простого типа не может содержать другие элементы или атрибуты. Комплексный тип может создавать эффект встраивания элементов в другие элементы или может ассоциировать атрибуты с элементом. До этого момента мы использовали только примеры с простыми типами, определенными пользователем (см. ProductCode). В спецификацию XML-схемы также включены предопределенные простые типы (см. вставку Простые типы). Предопределенный простой тип ограничивает значения по их базовому типу. К примеру, значением предопределенного простого типа ProductCode является подмножество значений базового типа string.

Простые, не вложенные элементы имеют простой тип

Элемент, который не содержит атрибутов или других элементов может быть отнесен к простому типу, предопределенному или определенному пользователем, такому как string, integer, decimal, time, ProductCode и т.п.

Листинг 7: Некоторые простые типы элементов
<element name='age' type='integer'/>
<element name='price' type='decimal'/>

Элементы с атрибутами должны иметь комплексный тип

Теперь попробуем добавить к простому элементу price из Листинга 7 атрибут currency. Вы не сможете этого сделать, так как элемент простого типа не может иметь атрибутов. Если вы хотите добавить атрибут, вам необходимо определить price как элемент комплексного типа. В примере из Листинга 8, мы определяем, так называемый анонимный тип, в котором комплексному типу не дается явного имени. Другими словами, атрибут name элемента complexType не определен.

Листинг 8: Элемент комплексного типа
<element name='price'>
  <complexType base='decimal' derivedBy='extension'>
    <attribute name='currency' type='string'/>
  </complexType>
</element>
<!-- In XML instance document, we can write: <price currency='US'>45.50</price> -->

Элементы, содержащие вложенные элементы должны иметь комплексный тип

В XML-документе в элемент могут быть вложены другие элементы. Это требование выражается напрямую в DTD. XML-схема вместо этого определяет элемент и его тип, который может включать объявления других элементов и атрибутов. Пример приведен в Таблице 1.

Таблица 1: Сравнение комплексных типов данных в DTD и XML-схеме

XML-документ
<Book>
   <Title>Cool XML<Title>
   <Author>Cool Guy</Author>
</Book>
DTD
<!ELEMENT Book (Title, Author)>
<!ELEMENT Title (#PCDATA)>
<!ELEMENT Author (#PCDATA)>
XML-схема
<element name='Book' type='BookType'/>
<complexType name='BookType'>
    <element name='Title' type='string'/>
    <element name='Author' type='string'/>
</complexType>

Несмотря на то, что XML-код в Таблице 1 соответствует обоим фрагментам DTD и XML-схемы, между ними существует большая разница. В DTD все элементы являются глобальными, тогда как XML-схема в таблице позволяет определить Title и Author локально, для появления их только в рамках элемента Book. Для точного повторения эффекта объявлений DTD в XML-схеме, элементы Title и Author должны иметь глобальную область действия, как это показано в Листинге 9. Атрибут ref элемента element позволяет ссылаться на предыдущие объявленные элементы.

Листинг 9: Комплексный тип, состоящий из глобальных простых типов
<element name='Title' type='string'/>
<element name='Author' type='string'/>
<element name='Book' type='BookType'/>
<complexType name='BookType'>
   <element ref='Title'/>
   <element ref='Author'/>
</complexType>

В примерах, представленных в Таблице 1 и Листинге 9, тип BookType является глобальным и может быть использован для объявления других элементов. В противоположность этому, в Листинге 10 элемент Book определяется как локальный анонимный тип. Обратите внимание, что фрагмент XML-документа из Таблицы 1 подходит для всех трех фрагментов схемы из Таблицы 1, Листинга 9 и Листинга 10.

Листинг 10: Скрытие BookType как локального типа
<element name='Title' type='string'/>
<element name='Author' type='string'/>
<element name='Book'>
   <complexType>
      <element ref='Title'/>
      <element ref='Author'/>
   </complexType>
</element>

Выражение сложных ограничений для элементов

XML-схема предлагает большую гибкость, чем DTD при выражении ограничений для модели контента элементов. На простейшем уровне, таком как в DTD, вы можете ассоциировать с элементом атрибуты, а также указать, что в нем может появляться последовательность из только одного (1), нуля или более (*), или одного или более (+) элементов из заданного набора элементов. В XML-схеме можно выразить дополнительные ограничения, используя для этой цели, к примеру, атрибуты minOccurs и maxOccurs для элемента element и элементы choice, group и all.

Листинг 11: Выражение ограничений для типов элементов
<element name='Title' type='string'/>
<element name='Author' type='string'/>
<element name='Book'>
   <complexType>
      <element ref='Title'/>
      <element ref='Author'/>
   </complexType>
</element>

В Листинге 11 тег Title является опциональным по отношению к тегу Book (такое же правило можно задать и в DTD). Однако здесь также говорится, что в элементе Book должен быть хотя бы один и не более двух элементов Author. Значением атрибутов minOccurs и maxOccurs тега element по умолчанию является 1. Элемент choice указывает на то, что может появиться только один из указанных дочерних элементов. Другой элемент all определяет, что все дочерние элементы могут появляться только один раз, вместе и в любом порядке, или не появляться совсем. В Листинге 12 объявляется, что оба тега Title и Author должны появляться в Book в любом порядке, или не появляться вообще. Подобные ограничения сложно выразить при помощи DTD.

Листинг 12: Указатель того, что у элемента должны быть определены все типы
<xsd:element name='Title' type='string'/>
<xsd:element name='Author' type='string'/>
<xsd:element name='Book'>
  <xsd:complexType>
    <xsd:all>
      <xsd:element ref='Tile'/>
      <xsd:element ref='Author'/>
    </xsd:all>
  </xsd:complexType>
</xsd:element>

Подведение итогов

В данном документе мы раскрыли при помощи простых примеров наиболее фундаментальные концепции, необходимые для определения структуры элементов при помощи XML-схемы. Доступно также множество других мощных механизмов:

  • XML-схема содержит всестороннюю поддержку для наследования типов, позволяя повторно использовать определенные ранее структуры. Такое использование называют аспектами. Вы можете вывести новые типы, представляющие меньшее подмножество значений других типов, к примеру, для определения подмножества по перечислению, диапазону или по совпадению с шаблоном. В одном из примеров данной статьи тип ProductCode был определен с использованием аспекта pattern. В подтипе также можно добавить для базового типа новые элементы и атрибуты.
  • Несколько механизмов, позволяющих контролировать общее определение подтипа или заменять его в определенном документе. К примеру, можно указать, что тип InvoiceType (тип номера инвойса) не может содержать подтипы, то есть никто не сможет определить новую версию InvoiceType. Можно также задать, что в отдельном контексте для типа ProductCode не может быть замещения подтипов.
  • Кроме использования подтипов, можно определять эквивалентные типы, то есть значение одного типа может быть замещено значением другого.
  • XML-схема обеспечивает механизм для замещения элемента или типа путем объявления их как абстрактных.
  • Для большего удобства можно обозначить и задать имена группам атрибутов или элементов. Это позволяет повторно использовать их при последующих обращениях.
  • XML-схема предоставляет три элемента – appInfo, documentation и annotation – для использования комментариев, как людьми (documentation) так и приложениями (appInfo)
  • Вы можете выразить уникальные ограничения, основывающиеся на определенных атрибутах дочерних элементов.

Дополнительную информацию по XML-схемам можно получить из документаций на сайтах W3C (См. Ресурсы по теме) и dW XML zone. Теперь, когда спецификация XML-схемы получила подтверждение в качестве кандидата на рекомендацию W3C, вы без сомнения можете использовать ее в полной мере.

Ресурсы

Комментарии

developerWorks: Войти

Обязательные поля отмечены звездочкой (*).


Нужен IBM ID?
Забыли Ваш IBM ID?


Забыли Ваш пароль?
Изменить пароль

Нажимая Отправить, Вы принимаете Условия использования developerWorks.

 


Профиль создается, когда вы первый раз заходите в developerWorks. Информация в вашем профиле (имя, страна / регион, название компании) отображается для всех пользователей и будет сопровождать любой опубликованный вами контент пока вы специально не укажите скрыть название вашей компании. Вы можете обновить ваш IBM аккаунт в любое время.

Вся введенная информация защищена.

Выберите имя, которое будет отображаться на экране



При первом входе в developerWorks для Вас будет создан профиль и Вам нужно будет выбрать Отображаемое имя. Оно будет выводиться рядом с контентом, опубликованным Вами в developerWorks.

Отображаемое имя должно иметь длину от 3 символов до 31 символа. Ваше Имя в системе должно быть уникальным. В качестве имени по соображениям приватности нельзя использовать контактный e-mail.

Обязательные поля отмечены звездочкой (*).

(Отображаемое имя должно иметь длину от 3 символов до 31 символа.)

Нажимая Отправить, Вы принимаете Условия использования developerWorks.

 


Вся введенная информация защищена.


static.content.url=http://www.ibm.com/developerworks/js/artrating/
SITE_ID=40
Zone=XML
ArticleID=96527
ArticleTitle=Основы использования XML-схем для определения элементов
publish-date=08012000