2011-09-21 40 views
5

XML belgesini doğrulamak için iç içe bir XSD şeması kullanıyorum. İçe aktarılan XSD'ler kendi hedef ad alanlarını kullanır ve Liquid XML Studio'yu kullanarak aşağıda verilen örnek XML'i doğrulayabilirim. Ancak, C# kodumu kullanarak doğrulama işlemini çalıştırdığımda, tür bildirim hatasıyla başarısız olur (aşağıya bakın). Ben anlamaya çalışıyorum çok zaman harcamak zorunda, ama hiçbir şanslar:İç içe XSD şemasını kullanarak XML doğrulama hatası - Tür bildirilmemiş

Ana XSD şeması (DataItem.xsd):

<?xml version="1.0" encoding="utf-8" ?> 
<xs:schema xmlns:DataNumeric="Doc.DataNumeric" xmlns:DataYesNo="Doc.DataYesNo" attributeFormDefault="qualified" elementFormDefault="qualified" xmlns:xs="http://www.w3.org/2001/XMLSchema"> 
    <xs:import schemaLocation="DataNumeric.xsd" namespace="Doc.DataNumeric" /> 
    <xs:import schemaLocation="DataYesNo.xsd" namespace="Doc.DataYesNo" /> 
    <xs:complexType name="tDataItem"> 
     <xs:choice> 
     <xs:element name="DataNumeric" type="DataNumeric:tDataNumeric" /> 
     <xs:element name="DataYesNo" type="DataYesNo:tDataYesNo" /> 
     </xs:choice> 
    </xs:complexType> 
    <xs:element name="DataItem" type="tDataItem" /> 
</xs:schema> 

Dahil XSD şeması (DataNumeric.xsd):

**<?xml version="1.0" encoding="utf-8" ?> 
<xs:schema xmlns:DataNumeric="Doc.DataNumeric" elementFormDefault="qualified" targetNamespace="Doc.DataNumeric" xmlns:xs="http://www.w3.org/2001/XMLSchema"> 
    <xs:complexType name="tDataNumeric"> 
    <xs:sequence> 
     <xs:element name="Answer" type="xs:double" /> 
    </xs:sequence> 
    </xs:complexType> 
    <xs:element name="DataNumeric" type="DataNumeric:tDataNumeric" /> 
</xs:schema>** 

XML:

<DataItem> 
    <DataNumeric xmlns:DataNumeric="Doc.DataNumeric"> 
    <DataNumeric:Answer>37.8</DataNumeric:Answer> 
    </DataNumeric> 
</DataItem> 

Doğrulama hatası:

XmlSchemaValidationException: Tür 'Doc.DataNumeric: tDataNumeric' bildirilmedi.

C# Doğrulama Kodu: Ben sinir bozucu bir gün sonra sorunu ve tekrarlamalar bir buçuk bulduk

XDocument xDoc = XDocument.Parse(xxxxxxx); 
string xsdPath = ConfigUtils.GetXsdPath(XsdSchemaIdentifier.HHDataItem); 
FileStream fs = new FileStream(xsdPath, FileMode.Open); 
XmlReader reader = XmlReader.Create(fs); 
XmlSchemaSet xss = new XmlSchemaSet(); 
xss.Add("", reader); 
fs.Close(); 
fs.Dispose(); 

xDoc.Validate(xss, null); 

cevap

5

. Değişen:

FileStream fs = new FileStream(xsdPath, FileMode.Open); 
XmlReader reader = XmlReader.Create(fs); 
XmlSchemaSet xss = new XmlSchemaSet(); 
xss.Add("", reader); 

XmlSchemaSet xss = new XmlSchemaSet(); 
xss.Add("", xsdPath); 

sorunu çözdü. Yine de hala NEDEN cevabını arıyorum? Her ikisi de şema kümesine bir şema eklemenin geçerli yoludur (yani 2 aşırı yük).

+5

Başarısız olmasının nedeni, XSD'nizin diğer XSD'leri içe aktarmasıdır. Bir 'XmlReader 'kullandığınızda, temel olarak' Aktarım 'girişinin konumunun ne olduğu hakkında hiçbir fikri yoktur ve bu nedenle, içe aktarmaları bulmak için herhangi bir yolu yoktur. Şema dosyasına giden yolu "XmlSchemaSet" 'e sağladığınızda, bu yola göre kendi yer belirleme çalışmasını yapabilir. – arootbeer

1

arootbeer, xsd'nizin başka bir xsd dosyasını nasıl içe aktardığı hakkında haklı bir şeydir. Ancak başka bir çözüm, içe aktarılan xsd'yi önce XmlSchemaSet'e eklemek, ardından gerçek içe aktarmayı yapan xsd'yi eklemektir. XmlSchemaSet ithal xsd eklerken

//Xsd file that is being imported 
FileStream importedXsdStream = new FileStream(importedXsdPath, FileMode.Open); 
XmlReader xmlReader = XmlReader.Create(importedXsdStream); 
XmlSchemaSet xmlSchemaSet = new XmlSchemaSet(); 
xmlSchemaSet.Add("NameSpace.SomeNameSpace", xmlReader); 

//Your code 
FileStream fs = new FileStream(xsdPath, FileMode.Open); 
XmlReader reader = XmlReader.Create(fs); 
XmlSchemaSet xss = new XmlSchemaSet(); 
xss.Add("", reader); 

Bildirim ben ilk parametre olarak Ad Alanı koydu. Bu, içe aktarılan xsd dosyasında sağlanan ad alanıyla eşleşmeyen hedef ad alanıyla ilgili hataların olup olmamasına bağlı olarak gerekli olabilir.

İlgili konular