验证 XSD 文件上的 XML 节点

本文关键字:XML 节点 XSD 文件 验证 | 更新日期: 2023-09-27 18:34:12

我正在尝试根据XML模式验证XML节点或片段。我读过这篇文章:

验证 xml 节点,而不是整个文档

但是选择的解决方案看起来不适合我。

private void ValidateSubnode(XmlNode node, XmlSchema schema)
{
  XmlTextReader reader = new XmlTextReader(node.OuterXml, XmlNodeType.Element, null);
  XmlReaderSettings settings = new XmlReaderSettings();
  settings.ConformanceLevel = ConformanceLevel.Fragment;
  settings.Schemas.Add(schema);
  settings.ValidationType = ValidationType.Schema;
  settings.ValidationEventHandler += new ValidationEventHandler(XSDValidationEventHandler);
  XmlReader validationReader = XmlReader.Create(reader, settings);
  while (validationReader.Read())
  {
  }
}
private void XSDValidationEventHandler(object sender, ValidationEventArgs args)
{
  errors.AppendFormat("XSD - Severity {0} - {1}", 
                  args.Severity.ToString(), args.Message);
}

据我所知,这是验证完整文档的代码,但带有"ConformanceLevel.Fragment"

因此,例如,具有像这样简单的架构:

<xsd:schema xmlns:xsd='http://www.w3.org/2001/XMLSchema'>
<xsd:element name="Customer">
  <xsd:complexType>
    <xsd:sequence>
      <xsd:element name="Address">
        <xsd:complexType>
          <xsd:sequence>
            <xsd:element name="Line1" type="xsd:string" />
            <xsd:element name="Line2" type="xsd:string" />
          </xsd:sequence>
       </xsd:complexType>
      </xsd:element>
    </xsd:sequence>
  </xsd:complexType>
</xsd:element>
</xsd:schema>

"根"节点验证是否正常

<Customer>
  <Address>
    <Line1>Foo</Line1>
    <Line2>Foo2</Line2>
  </Address>
</Customer>

但任何内部节点都不会验证

  <Address>
    <Line1>Foo</Line1>
    <Line2>Foo2</Line2>
  </Address>

我收到错误:"未声明'地址'元素"

我错过了什么吗?

验证 XSD 文件上的 XML 节点

您的架构不允许独立Address元素,因此当您仅通过时,验证将失败。

像这样修改架构:

<xsd:schema xmlns:xsd='http://www.w3.org/2001/XMLSchema'>
  <xsd:element name="Address">
    <xsd:complexType>
      <xsd:sequence>
        <xsd:element name="Line1" type="xsd:string" />
        <xsd:element name="Line2" type="xsd:string" />
      </xsd:sequence>
    </xsd:complexType>
  </xsd:element>
  <xsd:element name="Customer">
    <xsd:complexType>
      <xsd:sequence>
        <xsd:element ref="Address"/>
      </xsd:sequence>
    </xsd:complexType>
  </xsd:element>
</xsd:schema>
使用 XSD 验证

XML 片段并不真正有效:同一元素可以有效也可能无效 - 或者具有不同的有效结构 - 取决于它在与 XSD 匹配的文档中的位置,因此验证独立元素(通常)是不可能的。

根据 MiMo 的建议,为了解决这个问题,我在运行时修改了模式。我将其加载到内存中并在那里更改它。我在这里发布了我的解决方案:

使用辅助 XSD 文件根据架构验证 XML 节点