所以我尝试使用Microsoft提供的XMLDiff来查找两个XML文件之间的区别。目的是比较两个XML文件并找出确切的差异,以便我可以从中创建审计跟踪。文件可能具有不同的结构(添加或删除节点)。
然而,当涉及到嵌套的重复结构时,XMLDiff似乎给了我一个意想不到的输出。
示例XML#1(原始):
<pd:AP xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:pd="http://www.ascentn.com/bpm/XMLSchema">
<pd:processFields />
<pd:formFields>
<pd:TextBox1>val 1</pd:TextBox1>
<pd:DropdownList1>Option 4</pd:DropdownList1>
<pd:TextBox2>val 2</pd:TextBox2>
<pd:CheckBox1>Option 2;Option 3;Option 4</pd:CheckBox1>
<pd:SubForm1_SubForm>
<pd:SubForm1>
<pd:TextBox3>val 3</pd:TextBox3>
<pd:DropdownList3>Option 3</pd:DropdownList3>
<pd:DropdownList2>Option 2</pd:DropdownList2>
</pd:SubForm1>
<pd:SubForm1>
<pd:TextBox3>val 4</pd:TextBox3>
<pd:DropdownList3>Option 5</pd:DropdownList3>
<pd:DropdownList2>Option 3</pd:DropdownList2>
</pd:SubForm1>
</pd:SubForm1_SubForm>
</pd:formFields>
</pd:AP>
示例XML#2(已修改):
<pd:AP xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:pd="http://www.ascentn.com/bpm/XMLSchema">
<pd:processFields />
<pd:formFields>
<pd:TextBox1>val 1.changed</pd:TextBox1>
<pd:DropdownList1>Option 4</pd:DropdownList1>
<pd:TextBox2>val 2</pd:TextBox2>
<pd:CheckBox1>Option 2;Option 3;Option 4</pd:CheckBox1>
<pd:SubForm1_SubForm>
<pd:SubForm1>
<pd:TextBox3>val 3.changed</pd:TextBox3>
<pd:DropdownList3>Option 3</pd:DropdownList3>
<pd:DropdownList2>Option 2</pd:DropdownList2>
</pd:SubForm1>
<pd:SubForm1>
<pd:TextBox3>val 4</pd:TextBox3>
<pd:DropdownList3>Option 5</pd:DropdownList3>
<pd:DropdownList2>Option 11</pd:DropdownList2>
</pd:SubForm1>
<pd:SubForm1>
<pd:TextBox3>val 6</pd:TextBox3>
<pd:DropdownList3>Option 3</pd:DropdownList3>
<pd:DropdownList2>Option 3</pd:DropdownList2>
</pd:SubForm1>
</pd:SubForm1_SubForm>
</pd:formFields>
</pd:AP>
我得到的XML文件是:
<?xml version="1.0" encoding="utf-8"?>
<xd:xmldiff version="1.0" srcDocHash="12260906919056999448" options="IgnoreChildOrder IgnoreNamespaces IgnorePrefixes " fragments="no" xmlns:xd="http://schemas.microsoft.com/xmltools/2002/xmldiff">
<xd:node match="1">
<xd:node match="2">
<xd:node match="5">
<xd:add type="1" name="SubForm1" ns="http://www.ascentn.com/bpm/XMLSchema" prefix="pd">
<xd:add>
<pd:DropdownList2 xmlns:pd="http://www.ascentn.com/bpm/XMLSchema">Option 11</pd:DropdownList2>
</xd:add>
<xd:add match="/1/2/5/2/1-2" opid="1" />
</xd:add>
<xd:node match="1">
<xd:node match="1">
<xd:change match="1">val 3.changed</xd:change>
</xd:node>
</xd:node>
<xd:node match="2">
<xd:add>
<pd:TextBox3 xmlns:pd="http://www.ascentn.com/bpm/XMLSchema">val 6</pd:TextBox3>
<pd:DropdownList3 xmlns:pd="http://www.ascentn.com/bpm/XMLSchema">Option 3</pd:DropdownList3>
</xd:add>
<xd:remove match="1-2" opid="1" />
</xd:node>
</xd:node>
<xd:node match="1">
<xd:change match="1">val 1.changed</xd:change>
</xd:node>
</xd:node>
</xd:node>
<xd:descriptor opid="1" type="move" />
</xd:xmldiff>
这很奇怪,因为如果你看到pd的第二个节点:SubForm1,我只更改了其中的第3个元素。为什么它会在删除节点并再次添加时将其取出?难道它不会将其标记为更改吗?
如果我更改pd中的前两个节点:SubForm1然后它将其更改为已更改,但是一旦第3个节点(最后一个节点被更改),它就会将其标记为删除和添加(即使前两个节点未更改) )。
我设置了IgnoreChildOrder标志
XmlDiff xmldiff = new XmlDiff(XmlDiffOptions.IgnoreChildOrder |
XmlDiffOptions.IgnoreNamespaces |
XmlDiffOptions.IgnorePrefixes);
任何想法如何以更好的方式绕过这个或任何关于如何做到这一点的想法?
任何帮助都将受到高度赞赏。