在验证XML时键入catch

时间:2014-01-17 12:15:04

标签: c# xml excel xsd linq-to-xml

目前正在为涉及税务的公司工作,尝试将大量Excel文档解析为XML代码。没什么了不起的。问题在于用于验证解析的XML代码的XSD架构的开发人员。

这是事情变得疯狂的地方。在整个XSD中注意到编程效率的明显差异,至少涉及2个不同的开发人员(第二个是法语,因为他从使用英语名称转换为法语......)。现在为了这个问题。两个开发人员都喜欢使用他们自己的结构制作XSD Schema,其中一个使用1& 0用于验证复选框,另一个用于检查&选中。非常方便,因为所有的变量都是字母c + 4数字的组合..

所以终于来了问题!因为我正在使用Interop将所有内容解析为2个List,所以所有空值都记录为“”。这包括空复选框,空字符串,空日期。

在XDocument结构中实现节点之前,是否有可能检查节点的类型?通过这种方式,我可以检查传入节点是否来自复选框类型,并确保它处理“unchecked”字符串而不是空字符串,这将不会验证。

我的另一个解决方案是硬编码来自复选框类型的每一个代码,并且每次都运行一次比较。

xsd的一些代码显示我们正在谈论的内容..:

        <xs:element name="c1001" type="checkboxType" minOccurs="0"/>
        <xs:element name="c1002" type="checkboxType" minOccurs="0"/>
        <xs:element name="c1062" type="checkboxType" minOccurs="0"/>
        <xs:element name="c1028" type="checkboxType" minOccurs="0"/>>
        <xs:element name="c1035" type="numeric2Type" minOccurs="0"/>
        <xs:element name="c1054" type="numeric2Type" minOccurs="0"/>
        <xs:element name="c1055" type="numeric2Type" minOccurs="0"/>
        <xs:element name="c1036" type="numeric2Type" minOccurs="0"/>
        <xs:element name="c1037" type="numeric2Type" minOccurs="0"/>
        <xs:element name="c1058" type="numeric2Type" minOccurs="0"/>
        <xs:element name="c1059" type="numeric2Type" minOccurs="0"/>    
        <xs:element name="c1043" type="numeric2Type" minOccurs="0"/>
        <xs:element name="c1044" type="numeric2Type" minOccurs="0"/>
        <xs:element name="c1032" type="numeric2Type" minOccurs="0"/>
        <xs:element name="c1033" type="numeric2Type" minOccurs="0"/>    
        <xs:element name="c1100" type="numericu8D2Type" minOccurs="0"/>

我正在尝试解析的一些代码:

<c1002>checked</c1002>
<c1250>
  <valeur>227967.29</valeur>
</c1250>
<c1254>345.70</c1254>
<c1255>345.70</c1255>
<c1285>17410.44</c1285>
<c1286>
  <valeur>92583.46</valeur>
</c1286>
<c1287>731.28</c1287>

通过以下代码片段来处理验证:

 if (!IsValidXmlEx(nParsed,@"E:\Work\Resources\xsds\declaration_inr.xsd"))
            MessageBox.Show(Errors);
            else
            MessageBox.Show("Success");

public bool IsValidXmlEx(XDocument xmlDoc, string strXsdLocation)
    {
        bool bStatus = false;
        try
        {
            // Declare local objects
            XmlReaderSettings rs = new XmlReaderSettings();
            rs.ValidationType = ValidationType.Schema;
            rs.ValidationFlags |= XmlSchemaValidationFlags.ProcessSchemaLocation | XmlSchemaValidationFlags.ReportValidationWarnings;
            rs.ValidationEventHandler += new ValidationEventHandler(rs_ValidationEventHandler);
            rs.Schemas.Add(null, XmlReader.Create(strXsdLocation));

            using (XmlReader xmlValidatingReader = XmlReader.Create(xmlDoc.CreateReader(), rs))
            { while (xmlValidatingReader.Read()) { } }

            ////Exception if error.
            if (nErrors > 0) { throw new Exception(strErrorMsg); }
            else { bStatus = true; }//Success
        }
        catch (Exception error) { bStatus = false; }

        return bStatus;
    }

 void rs_ValidationEventHandler(object sender, ValidationEventArgs e)
    {
        if (e.Severity == XmlSeverityType.Warning) strErrorMsg += "WARNING: " + Environment.NewLine;
        else strErrorMsg += "ERROR: " + Environment.NewLine;
        nErrors++;
        strErrorMsg = strErrorMsg + e.Exception.Message + "\r\n";
    }

1 个答案:

答案 0 :(得分:2)

看起来您从Excel获得的XML在架构方面完全无效。看起来Excel将所有导出的值视为类型字符串。

如果发生了这种情况,那么我建议没有什么好办法可以解决这个问题。你要么:

  1. 更新Excel导出,以便输出有效的XML(相对于架构)。
  2. 将您的Excel输出转换为另一个XML实例,然后可以根据架构验证(可能使用xslt),或
  3. 以代码或其他方式进行验证,或
  4. 根本不验证输出。
  5. 无论如何,没有&#34;技巧&#34;我知道允许无效的XML对XSD进行验证。

    对不起,这可能不是你想要的答案。

    <强>更新

    好的 - XSD架构描述了XML文档的外观。它定义了该文档中合法的类型。任何针对XSD架构验证的XML文档都可以说是一个&#34;架构实例&#34;那个架构。

    在您的情况下,XSD定义了一个带有字段(c1035,c1036等)及其类型的类型。上面的架构示例中的每种类型都显示为自定义类型,应在XSD的其他位置定义。

    但是,&gt; schema-instance&#34;,在您的情况下是Excel的输出,不会验证。

    让我们以XML输出为例:

    <c1002>checked</c1002> 
    

    如果我们查看架构代码段,我们可以看到以下内容:

    <xs:element name="c1001" type="checkboxType" minOccurs="0"/>
    

    这告诉我的是,架构中某处有一个名为 checkboxType 的类型。此类型可以在同一模式中内联,也可以在此模式引用的另一个模式中定义。

    现在, checkboxType 可能已经定义了任何模式实例文档的字段 c1002 中的数据的一组允许值,例如&#34;选中&#34;,&#34;取消选中&#34;。

    如果字段中的值不是&#34;有效&#34;根据类型定义,架构实例无效。

    当您针对xml输出运行xsd验证时,会发生这种情况,除了每个字段。某处,根据XSD架构中定义的类型定义,输出的数据不正确。

    由于您没有提供任何错误消息,因此无法确切知道失败的确切位置,但根据您在前50或60个字段之后的某个地方发表评论。