针对多个模式验证未知 xml,直到找到匹配项

Dav*_*idB 4 c# xml xsd linq-to-xml

我已将 xml 发送到网页,并且想针对多个 xsd 进行验证,直到文件验证为止。当它验证时,我将能够根据验证它的模式来确定 xml 文件的类型。

  List<string> xsdList = new List<string>();

  xsdList.Add(_path + @"Handlers\DeviceSpecificHandlers\Schemas\Enquiry.xsd");
  xsdList.Add(_path + @"Handlers\DeviceSpecificHandlers\Schemas\FingerDeleted.xsd");
  xsdList.Add(_path + @"Handlers\DeviceSpecificHandlers\Schemas\Heartbeat.xsd");
  xsdList.Add(_path + @"Handlers\DeviceSpecificHandlers\Schemas\Validation.xsd");

  XmlSchemaSet schemas = new XmlSchemaSet();

  foreach (string schema in xsdList)
  {
    var reader = new StringReader(File.ReadAllText(schema));
    schemas.Add("", XmlReader.Create(reader));
  }

  request.Validate(schemas, (o, e) =>
  {
    match = false;
  });
Run Code Online (Sandbox Code Playgroud)

任何人都可以帮忙,上面是我到目前为止拼凑在一起的内容,它当前抛出错误“System.Xml.Schema.XmlSchemaValidationException:全局元素“接口”已被声明”

有没有办法获得哪个模式验证成功的返回?

Pet*_*dea 5

首先,您必须弄清楚哪些 XSD 文件可以放在一个文件集中。您收到的错误告诉您相同的元素“interface”具有来自两个或多个不同基本 URI 的定义。

如果您想动态确定集合,那么您需要做一些工作。这是可能的,但并非微不足道。这取决于 XSD 文件是否使用组合(包含/导入/重新定义)。如果他们不这样做(简单的场景),那么为了将 XSD 文件放在一起,您必须单独加载每个 XSD 文件,构建所有全局定义内容(类型、元素、组、属性、属性组)的索引,然后将将这些集中在集合中,使得给定集合中的任何一对单独的 XSD 成员,交集为空。构建集合的策略取决于许多因素,性能和覆盖范围只是其中的两个因素。基于这个简单的案例,您可以看到组合如何变得重要,因为现在即使交集不为空,如果公共内容来自相同的 URI,所有意图都将被视为空。

QTAssistant(我与它相关)有一个完整的引擎来处理上述问题,以便在“收获”任意 XSD 内容进行分析、验证等时为其 XML 模式重构引擎设置 XML 模式源集(或集合) 。

一旦你弄清楚了这些集合,你就必须对这些模式的组成做出假设。换句话说,有效 XML 文档元素集的构成是什么(有时并非所有全局元素定义都是有效的文档元素),以及每个文档元素应该使用什么模式集。很明显,您必须以某种方式处理这个问题,因为您有重复的元素。

如果您想根据您的问题处理它,则只需循环遍历如上所述构造的模式集集即可。

提出如何手动找出最佳集的策略的最佳方法可能是可视化 XSD 文件之间的关系。下面是我如何使用可用的工具来看待它的说明,来自 SO 的另一篇文章。

在此输入图像描述