2016-06-20 2 views
2

Я пытаюсь создать схему XSD для XML-документа, который я получил, однако есть два элемента: staff, которые имеют одинаковое имя.Создание схемы XML для элементов с тем же именем?

Есть ли способ создать схему для этого XML, хотя есть два элемента с тем же именем?

XML:

<contacts> 
    <staff count="248" pagesize="284"> 
    <staff id="1231"> 
    <Forename>test</Forename> 
    <Surname>test</Surname> 
    <DateOfBirth>0000-00-00</DateOfBirth> 
    <Gender/> 
    <Address1/> 
    <Address2/> 
    <Town/> 
    <County/> 
    <Telephone/> 
    <Mobile/> 
    <Email/> 
    <Created>0000-06-18 09:46:32</Created> 
    <CreatedBy>test</CreatedBy> 
    <Updated>2000-06-18 09:46:32</Updated> 
    <UpdatedBy>test</UpdatedBy> 
    <Archived>0000-00-00 00:00:00</Archived> 
    <ArchivedBy/> 
    <Postcode/> 
    <Age>0</Age> 
    <RestrictedRecord>0</RestrictedRecord> 
    <Disability_S_24/> 
    <Ethnicity_S_25/> 
    <Type>8</Type> 
    <PersonID>1231</PersonID> 
    <TypeName>staff</TypeName> 
    </staff> 
</staff> 
</contacts> 

схемы до сих пор:

<?xml version="1.0" encoding="utf-8" standalone="no"?> 
<xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema" elementFormDefault="qualified"> 
    <xs:element name="contacts"> 
     <xs:complexType> 
      <xs:sequence> 
       <xs:element ref="staff"/> 
      </xs:sequence> 
     </xs:complexType> 
    </xs:element> 
    <xs:element name="staff"> 
     <xs:complexType> 
      <xs:sequence> 
       <xs:element maxOccurs="unbounded" ref="staff"/> 
      </xs:sequence> 
      <xs:attribute name="count" use="required" type="xs:integer"/> 
      <xs:attribute name="pagesize" use="required" type="xs:integer"/> 
     </xs:complexType> 
    </xs:element> 
    <xs:element name="staff"> 
     <xs:complexType> 
      <xs:all > 
       <xs:element ref="Forename" minOccurs="0"/> 
       <xs:element ref="Surname" minOccurs="0"/> 
       <xs:element ref="DateOfBirth" minOccurs="0"/> 
       <xs:element ref="Gender" minOccurs="0"/> 
       <xs:element ref="Address1" minOccurs="0"/> 
       <xs:element ref="Address2" minOccurs="0"/> 
       <xs:element ref="Town" minOccurs="0"/> 
       <xs:element ref="County" minOccurs="0"/> 
       <xs:element ref="Telephone" minOccurs="0"/> 
       <xs:element ref="Mobile" minOccurs="0"/> 
       <xs:element ref="Email" minOccurs="0"/> 
       <xs:element ref="Created" minOccurs="0"/> 
       <xs:element ref="CreatedBy" minOccurs="0"/> 
       <xs:element ref="Updated" minOccurs="0"/> 
       <xs:element ref="UpdatedBy" minOccurs="0"/> 
       <xs:element ref="Archived" minOccurs="0"/> 
       <xs:element ref="ArchivedBy" minOccurs="0"/> 
       <xs:element ref="Postcode" minOccurs="0"/> 
       <xs:element ref="Age" minOccurs="0"/> 
       <xs:element ref="RestrictedRecord" minOccurs="0"/> 
       <xs:element ref="Disability_S_24" minOccurs="0"/> 
       <xs:element ref="Ethnicity_S_25" minOccurs="0"/> 
       <xs:element ref="Education_V_2" minOccurs="0"/> 
       <xs:element ref="EmploymentTrainingStatus_V_1" minOccurs="0"/> 
       <xs:element ref="Type" minOccurs="0"/> 
       <xs:element ref="PersonID" minOccurs="0"/> 
       <xs:element ref="TypeName" minOccurs="0"/> 
      </xs:all> 
      <xs:attribute name="id" use="required" type="xs:integer"/> 
     </xs:complexType> 
    </xs:element> 
    <xs:element name="Forename" type="xs:string"/> 
    <xs:element name="Surname" type="xs:string"/> 
    <xs:element name="DateOfBirth" type="xs:NMTOKEN"/> 
    <xs:element name="Gender" type="xs:string"/> 
    <xs:element name="Address1" type="xs:string"/> 
    <xs:element name="Address2" type="xs:string"/> 
    <xs:element name="Town" type="xs:string"/> 
    <xs:element name="County" type="xs:string"/> 
    <xs:element name="Telephone" type="xs:string"/> 
    <xs:element name="Mobile" type="xs:string"/> 
    <xs:element name="Email" type="xs:string"/> 
    <xs:element name="Created" type="xs:string"/> 
    <xs:element name="CreatedBy" type="xs:NCName"/> 
    <xs:element name="Updated" type="xs:string"/> 
    <xs:element name="UpdatedBy" type="xs:NCName"/> 
    <xs:element name="Archived" type="xs:string"/> 
    <xs:element name="ArchivedBy" type="xs:string"/> 
    <xs:element name="Postcode" type="xs:string"/> 
    <xs:element name="Age" type="xs:integer"/> 
    <xs:element name="RestrictedRecord" type="xs:integer"/> 
    <xs:element name="Disability_S_24"> 
     <xs:complexType/> 
    </xs:element> 
    <xs:element name="Ethnicity_S_25"> 
     <xs:complexType/> 
    </xs:element> 
    <xs:element name="Type" type="xs:integer"/> 
    <xs:element name="PersonID" type="xs:integer"/> 
    <xs:element name="TypeName" type="xs:NCName"/> 
</xs:schema> 

ответ

0

Ваше форматирование меня отбросило - я изначально исправил его в своем вопросе, но изменил свое мнение, поскольку, по-моему, это важная деталь для вашего вопроса. У вас фактически нет двух элементов sibling staff (я заметил это, когда искал закрывающие теги), у вас есть ребенок с таким же именем, что и его родитель. Хорошо.Вот ваш Измененный XML:

<contacts> 
    <staff count="248" pagesize="284"> 
     <staff id="1231"> 
      <Forename>test</Forename> 
      <Surname>test</Surname> 
      <DateOfBirth>0000-00-00</DateOfBirth> 
      <Gender/> 
      <Address1/> 
      <Address2/> 
      <Town/> 
      <County/> 
      <Telephone/> 
      <Mobile/> 
      <Email/> 
      <Created>0000-06-18 09:46:32</Created> 
      <CreatedBy>test</CreatedBy> 
      <Updated>2000-06-18 09:46:32</Updated> 
      <UpdatedBy>test</UpdatedBy> 
      <Archived>0000-00-00 00:00:00</Archived> 
      <ArchivedBy/> 
      <Postcode/> 
      <Age>0</Age> 
      <RestrictedRecord>0</RestrictedRecord> 
      <Disability_S_24/> 
      <Ethnicity_S_25/> 
      <Type>8</Type> 
      <PersonID>1231</PersonID> 
      <TypeName>staff</TypeName> 
     </staff> 
    </staff> 
</contacts> 

Тем не менее, вы не можете построить схему так, как вы его прямо сейчас - об этом думать, что staff элемент является то, что ref в виду? Как мог любой синтаксический анализатор XSD узнать, какой он?

Я думаю, что самый простой способ исправить вашу схему будет сделать следующее:

<?xml version="1.0" encoding="utf-8" standalone="no"?> 
<xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema" elementFormDefault="qualified"> 
    <xs:element name="contacts"> 
     <xs:complexType> 
      <xs:sequence> 
       <xs:element ref="staff"/> 
      </xs:sequence> 
     </xs:complexType> 
    </xs:element> 
    <xs:element name="staff"> 
     <xs:complexType> 
      <xs:sequence> 
       <xs:element maxOccurs="unbounded" name="staff" type="staffInner"/> 
      </xs:sequence> 
      <xs:attribute name="count" use="required" type="xs:integer"/> 
      <xs:attribute name="pagesize" use="required" type="xs:integer"/> 
     </xs:complexType> 
    </xs:element> 
    <xs:complexType name="staffInner"> 
     <xs:all> 
     .... 

Я бы выбрал лучшее название, чем staffInner, если у меня было немного больше контекста - может быть что-то вроде individualStaffMember? Я также могу поменять ваш другой ref, чтобы вместо этого использовать type.

Кроме того, вы уверены, что хотите xs:all, а не только xs:sequence? Если вы сохраняете xs:all, то minOccurs="0" избыточен на всех этих дочерних элементах. Если вы имеете в виду, что xs:sequence (что, как я подозреваю, возможно, так оно и есть), но будьте осторожны, потому что xs:all позволит элементам появляться в любом порядке ...

+0

Спасибо за ответ. Я сделал эту поправку и, похоже, сработал. Im использует , поскольку в зависимости от типа «Тип» используются только определенные элементы. –

+0

Вы могли бы выполнить это с помощью последовательности и minOccurs –

1

A. Если у вас есть контроль над как XSD и XML-, вот варианты наличия двух элементов staff с разным nt в вашем XML:

  1. Используйте пространства имен, чтобы их отличить.
  2. Переименовать один из них.

B. Если у вас есть контроль над XSD но не XML-, вот несколько вариантов:

  1. Использование локальных определений. (Два глобально определенных элемента не могут иметь одно и то же имя, но это нормально, если один или оба локально определены.) [Рекомендовано, если вы действительно хотите использовать одно и то же имя.]
  2. Объедините две модели контента, в общем случае требуются, а компоненты, которые являются отдельными, являются необязательными. (Если контекст различает две модели содержимого, при необходимости добавить XSD 1.1 утверждения для обеспечения дифференциации.)

Вот полностью исправлен XSD с помощью опции В.1:

<?xml version="1.0" encoding="utf-8" standalone="no"?> 
<xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema" 
      elementFormDefault="qualified"> 
    <xs:element name="contacts"> 
    <xs:complexType> 
     <xs:sequence> 
     <xs:element ref="staff"/> 
     </xs:sequence> 
    </xs:complexType> 
    </xs:element> 
    <xs:element name="staff"> 
    <xs:complexType> 
     <xs:sequence> 
     <xs:element name="staff" maxOccurs="unbounded"> 
      <xs:complexType> 
      <xs:all> 
       <xs:element ref="Forename" minOccurs="0"/> 
       <xs:element ref="Surname" minOccurs="0"/> 
       <xs:element ref="DateOfBirth" minOccurs="0"/> 
       <xs:element ref="Gender" minOccurs="0"/> 
       <xs:element ref="Address1" minOccurs="0"/> 
       <xs:element ref="Address2" minOccurs="0"/> 
       <xs:element ref="Town" minOccurs="0"/> 
       <xs:element ref="County" minOccurs="0"/> 
       <xs:element ref="Telephone" minOccurs="0"/> 
       <xs:element ref="Mobile" minOccurs="0"/> 
       <xs:element ref="Email" minOccurs="0"/> 
       <xs:element ref="Created" minOccurs="0"/> 
       <xs:element ref="CreatedBy" minOccurs="0"/> 
       <xs:element ref="Updated" minOccurs="0"/> 
       <xs:element ref="UpdatedBy" minOccurs="0"/> 
       <xs:element ref="Archived" minOccurs="0"/> 
       <xs:element ref="ArchivedBy" minOccurs="0"/> 
       <xs:element ref="Postcode" minOccurs="0"/> 
       <xs:element ref="Age" minOccurs="0"/> 
       <xs:element ref="RestrictedRecord" minOccurs="0"/> 
       <xs:element ref="Disability_S_24" minOccurs="0"/> 
       <xs:element ref="Ethnicity_S_25" minOccurs="0"/> 
       <xs:element ref="Education_V_2" minOccurs="0"/> 
       <xs:element ref="EmploymentTrainingStatus_V_1" minOccurs="0"/> 
       <xs:element ref="Type" minOccurs="0"/> 
       <xs:element ref="PersonID" minOccurs="0"/> 
       <xs:element ref="TypeName" minOccurs="0"/> 
      </xs:all> 
      <xs:attribute name="id" use="required" type="xs:integer"/> 
      </xs:complexType> 
     </xs:element> 
     </xs:sequence> 
     <xs:attribute name="count" use="required" type="xs:integer"/> 
     <xs:attribute name="pagesize" use="required" type="xs:integer"/> 
    </xs:complexType> 
    </xs:element> 
    <xs:element name="Forename" type="xs:string"/> 
    <xs:element name="Surname" type="xs:string"/> 
    <xs:element name="DateOfBirth" type="xs:NMTOKEN"/> 
    <xs:element name="Gender" type="xs:string"/> 
    <xs:element name="Address1" type="xs:string"/> 
    <xs:element name="Address2" type="xs:string"/> 
    <xs:element name="Town" type="xs:string"/> 
    <xs:element name="County" type="xs:string"/> 
    <xs:element name="Telephone" type="xs:string"/> 
    <xs:element name="Mobile" type="xs:string"/> 
    <xs:element name="Email" type="xs:string"/> 
    <xs:element name="Created" type="xs:string"/> 
    <xs:element name="CreatedBy" type="xs:NCName"/> 
    <xs:element name="Updated" type="xs:string"/> 
    <xs:element name="UpdatedBy" type="xs:NCName"/> 
    <xs:element name="Archived" type="xs:string"/> 
    <xs:element name="ArchivedBy" type="xs:string"/> 
    <xs:element name="Postcode" type="xs:string"/> 
    <xs:element name="Age" type="xs:integer"/> 
    <xs:element name="RestrictedRecord" type="xs:integer"/> 
    <xs:element name="Disability_S_24"> 
    <xs:complexType/> 
    </xs:element> 
    <xs:element name="Ethnicity_S_25"> 
    <xs:complexType/> 
    </xs:element> 
    <xs:element name="Education_V_2"> 
    <xs:complexType/> 
    </xs:element> 
    <xs:element name="EmploymentTrainingStatus_V_1"> 
    <xs:complexType/> 
    </xs:element> 
    <xs:element name="Type" type="xs:integer"/> 
    <xs:element name="PersonID" type="xs:integer"/> 
    <xs:element name="TypeName" type="xs:NCName"/> 
</xs:schema> 

Это XSD будет успешно проверить ваш XML.

+0

Спасибо за ответ. Я не контролирую сам XML-документ, у меня есть только API-интерфейс для сбора данных. Если я просто переименую элементы в Схеме, будет ли это работать? –

+0

Нет, извините, переименование элементов в одностороннем порядке в XSD не будет работать. Ответ обновляется, чтобы различать, есть ли у вас контроль над XML или нет. – kjhughes

+0

Можете ли вы представить пример объединения двух моделей контента? Я стараюсь много чего, но не добился успеха. –

1

Если два элемента родства имеют одинаковое имя, тогда в XSD есть правило («декларации элементов согласованы»), в которых говорится, что они также должны иметь один и тот же тип.

Однако, если элементы отображаются в разных местах XML, а не как братья и сестры (например, персонал/персонал или контакты/персонал), то они могут иметь разные типы; это может быть достигнуто с помощью локальных деклараций элементов.

Смежные вопросы