我正在使用MSXML 6.0将自己的XML转换为另一种XML格式。我不确定我是否只是不清楚MSXML是如何工作的,但我相信我已经注意到它有一些奇怪的行为……
我将使用
setProperty
方法例如
XmlDocument.setProperty('SelectionNamespaces',
' xmlns:ms=''http://mydomain.com/2010/MySchema''');
然后,我使用自己的自定义序列化程序在内存中构建XML(而不是保存到磁盘)。序列化后,我将加载到XSLT文件中,并使用
transformNodeToObject
例如
AppXmlDoc.transformNodeToObject(XslXmlDoc, AStreamForTransformedXml);
问题是转换正在工作,但没有一个特定的模板与我在其中使用的xpath匹配。我通过Visual Studio运行带有测试数据的XSLT文件,消除了它本身的任何问题,并且它按预期工作。然后我假设这一定是一个编码问题,所以我确保所有涉及到的文档都是以utf-8的形式读/写的……仍然没有运气。
下面是转换的示例:
<?xml version="1.0" encoding="utf-8"?>
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform" xmlns:ms="http://mydomain.com/2010/MySchema" exclude-result-prefixes="ms">
<xsl:template match="/">
<ARoot>
<head>
<xsl:apply-templates select="ms:Element/ms:SubElement" />
</head>
<body>
<xsl:apply-templates select="ms:Element/ms:DifferentSubElement" />
</body>
</ARoot>
因此,在运行MSXML时转换的结果会带来基本结构,但不包括任何模板数据。经过一些测试,我发现让它工作的唯一方法是按以下步骤进行:
-
新建XML文档
-
使用设置命名空间信息
setProperty
-
序列化XML并保存到磁盘。
-
关闭文档-
额外步骤
-
新建XML文档-
额外步骤
-
重新加载文档-
额外步骤
-
重新设置命名空间信息-
额外步骤
-
执行转换。
因此,MSXML在某个时刻似乎会失去对名称空间信息的跟踪。更奇怪的是,即使您重置了名称空间信息(序列化之后)并尝试转换,它仍然不起作用!只有当我保存文档、关闭它并重新创建一个新的XML文档并将其加载回(因此,我需要重置命名空间)时,它才会工作。
有人对此有什么想法吗?