Example of a Diffgram

Microsoft XML Diff

Microsoft XML Diff 1.0 and XML Patch 1.0

Example of a Diffgram

The following table shows two XML documents: one is the source and the other is the changed document. These documents are the input to a Compare method that creates an XDL Diffgram. The line number shown is added for readability purposes.

Line number Source XML document Line number Changed XML document
1 <?xml version="1.0"?> 1 <?xml version="1.0"?>
2 <b> 2 <b>
3   <a>Some text 1</a> 3   <yy>Some text 1</yy>
4   <b>Some text 2</b> 4   <b>Some text 2</b>
5   <c>Some text 3</c> 5   <c>Some text 3</c>
6   <d> 6   <e>Some text 4</e>
7     Another text 7   <f>Some text 5</f>
8     <fob/> 8   <d>Changed text</d>
9   </d> 9   <x firstAttr="changed attribute value" newAttr="new value"/>
10   <x firstAttr="value1" secondAttr="value2"/> 10   <p>
11   <y> 11     <q>
12     <!--Any comments?--> 12         <y>
13     <z id="10">Just another text</z> 13           <!--Any comments?-->
14   </y> 14           <z id="10">Just another text</z>
15 </b> 15         </y>
16   16     </q>
17   17   </p>
18   18
19   19 </b>

Following is the XDL Diffgram produced when a Compare method is run against the two documents shown in the preceding table. The line number is added for readability purposes.

Line number XDL Diffgram output
1 <?xml version="1.0" encoding="utf-16"?>
2 <xd:xmldiff version="1.0" srcDocHash="5346998544451918424" options="None" xmlns:xd="http://schemas.microsoft.com/xmltools/2002/xmldiff">
3   <xd:node match="2">
4     <xd:change match="1" name="yy" />
5     <xd:node match="3" />
6     <xd:add>
7       <e>Some text 4</e>
8       <f>Some text 5</f>
9     </xd:add>
10     <xd:node match="4">
11       <xd:change match="1">Changed text</xd:change>
12       <xd:remove match="2" />
13     </xd:node>
14     <xd:node match="5">
15       <xd:remove match="@secondAttr" />
16       <xd:add type="2" name="newAttr">new value</xd:add>
17       <xd:change match="@firstAttr">changed attribute value</xd:change>
18     </xd:node>
19     <xd:remove match="6" opid="1" />
20     <xd:add type="1" name="p">
21       <xd:add type="1" name="q">
22         <xd:add match="/2/6" opid="1" />
23       </xd:add>
24     </xd:add>
25   </xd:node>
26   <xd:descriptor opid="1" type="move" />
27 </xd:xmldiff>

The following list shows each line in the XDL Diffgram output from the preceding table. Here you can see why each line was generated.

Line 1: is required to create a well-formed XML document.

Line 2: is the root element of the XDL Diffgram xd:xmldiff. It contains the version of the XDL Diffgram in the version attribute, the XDL namespace declaration for the xd: prefix, and the XML Diff options selected when the XDL Diffgram was created in the options attribute. It also contains srcDocHash attribute with a number that is calculated from the source document and is called a hash value. This number allows checking if an XML document is the correct source document the XDL Diffgram was created on. This check is performed by XML Patch tool.

Line 3: is an xd:node element with a match attribute containing a path descriptor pointing to the second element at the source tree root level, which is the <b> element on line 2 on the source document. It indicates that there will be some changes described on either the child nodes of the <b> element, or on the sibling nodes following the <b> element, or both. In this particular case, the child nodes of xd:node describes the changes on the child nodes of the <b> element.

Line 4: indicates a change has occurred. The changed node is identified with a path descriptor "1" which points to <a>, the first child node of the <b> element. The name attribute is the new local name for the node. In this particular case, the xd:change is indicating that element <a> in the source document has been changed to an element with a name of "yy" in the new document.

Line 5: is an xd:node element with a match attribute containing a path descriptor pointing to the third child node of the <b> element, which is the <c> element. The path descriptor is relative to the xd:node match element that it is nested under, so it is pointing to the third child node (<c> element) under the second node at root level (<b> element, see line 3). In this case, the xd:node has no child nodes and it is indicating that there will be some changes described on the following sibling nodes. In other words, it indicates that something is happening, starting at this location.

Line 6: indicates an add operation, which is occurring under after the <c> element of the source document. The <c> element has been specified by the previous <xd:node> operation (line 5). Note that there are no attributes associated with the xd:add, so the content of this element is the new fragment that has been added in the changed document.

Line 7-8: shows the XML fragment that has been added in the changed document after the <c> element. It adds the <e> and <f> element from lines 6-7 of the changed document.

Line 9: is an end element, indicating the end of the add operation.

Line 10: is a match operation, with its path descriptor pointing to the fourth child node. They are still nested under the match operation from line 3, which is a match of element 2, the <b> element, so the fourth child node under the <b> element is the <d> element. It is now pointing at the <d> element. The child nodes of the xd:node element will describe changes of the child nodes of the <d> element.

Line 11: xd:change element that indicates that a change has occurred. The changed node is identified with a path descriptor "1" that points to the first child node of the <d> element, which is a text node, "Another text" (line 7 of the source document). The content of the xd:change element is the new value of the text node.

Line 12: xd:remove element that indicates a node has been removed. The path descriptor points to the second child node of the <d> element, which is the <fob/> element. So this indicates that the <fob/> element has been removed and is no longer present in the changed document.

Line 13: is the end element for the xd:node element from line 10. Now you see they are nested under the <b> element again.

Line 14: is an xd:node element with the path descriptor pointing to the fifth child node of the <b> element, which is the <x> element. The child nodes of this xd:node element will describe changes of the child nodes of the <x> element.

Line 15: is a remove operation, and is using a path descriptor that contains the "@" symbol. The "@" symbol indicates that the patch descriptor points to an attribute. The attribute name follows the "@" symbol and it is "secondAttr". So this xd:remove element is showing the removal of the secondAttr attribute from the <x> element.

Line 16: shows an add operation on a node type of 2, which is the addition of an attribute node. Its name is newAttr and the value is "new value". So in the changed document the <x> element has a new attribute with the name newAttr and value of "new value". This is shown in the changed document on line 9.

Line 17: shows a change operation. The match attribute indicates that the change is occurring to the attribute named "firstAttr", and the content shows the new value of the attribute. This indicates that in the changed document the "firstAttr" attribute has its value changed to "changed attribute value". The old attribute value of "value1" has been replaced. The old attribute value is seen in the original document at line 10. The new, modified value is shown in the changed document at line 9.

Line 18: is the end of the xd:node element from line 14. Now you can see that they are nested under the <b> element again.

Line 19: is a remove operation of the sixth child node of the <b> element, which is the <y> element (and all its descendant nodes). Notice that there is an opid, so this remove operation is part of an extended operation. The extended operation will be found later in the XDL Diffgram under an xd:descriptor element with the same opid. Line 26 is the xd:descriptor with the matching opid, and shows that this remove operation is part of a larger move operation.

Line 20: is an add operation, adding a node of type 1, which is an element node. The new element name is "p". This new element is shown in the modified document at line 10. The child nodes of this <xd:add> element describes the child nodes of the new <p> element. So you can see that they now nested under the <p> element.

Line 21: is an add operation, adding a node of type 1, which is an element node. The new element name is "q". This new element is shown in the modified document at line 11. The <q> element is a child of the <p> element. The child nodes of this <xd:add> element describes the child nodes of the <q> element. Now they are nested under the <q> element.

Line 22: is an add operation with a path descriptor /2/6, which is an absolute path descriptor. It points to the sixth child node of the second node at root level, which is the <y> element shown in the original document at line 11. Note that the xd:add operation has an opid attribute, so this operation is part of an extended operation. The extended operation will be found later in the XDL Diffgram under an xd:descriptor element with the same opid. Line 26 is the xd:descriptor with the matching opid, and shows that this add operation is part of a larger move operation.

Line 23: is an end element, ending the xd:add operation from line 21. Now they are nested under the <p> element.

Line 24: is an end element, ending the xd:add operation from line 20. Now they are nested under the <b> element.

Line 25: is an end element, ending the xd:node from line 3. Now they are nested under the original document root node.

Line 26: is an xd:descriptor describing an extended operation. It shows an operation ID of "1" in the opid attribute and the type of the operation "move" in the type attribute. It means that there is a remove and add operation somewhere in the XDL Diffgram, both with an opid of "1", and it indicates that an existing node was removed from the original document and added back into a different spot in the changed document, which is basically a move operation. Reviewing the XDL Diffgram, the moved node was the <y> node (and all its descendants) at line 11 of the original document. In the XDL Diffgram, there is a remove operation with an opid attribute value of 1 back at line 18, and an add operation back at line 22. The <y> element has been moved to line 12 in the changed document.

Line 27: indicates the end of the xd:xmldiff element, and the end of the XDL Diffgram.

See Also

XML Diff Functionality | Running Comparisons Between Documents, Fragments, or Nodes | Setting Options that Affect the Comparison | Selecting the Algorithm for the Comparison | Limitations | XML Diff Language (Diffgram) | Path Descriptors | Extended Operations |XmlDiff Class

© 2002 Microsoft Corporation. All rights reserved.