コード例 #1
0
        private NodePosition CompareElements(XmlDiffElement elem1, XmlDiffElement elem2)
        {
            Debug.Assert(elem1 != null);
            Debug.Assert(elem2 != null);
            int nCompare = 0;

            if ((nCompare = CompareText(elem2.LocalName, elem1.LocalName)) == 0)
            {
                if (IgnoreNS || (nCompare = CompareText(elem2.NamespaceURI, elem1.NamespaceURI)) == 0)
                {
                    if (IgnorePrefix || (nCompare = CompareText(elem2.Prefix, elem1.Prefix)) == 0)
                    {
                        if ((nCompare = CompareText(elem2.Value, elem1.Value)) == 0)
                        {
                            if ((nCompare = CompareAttributes(elem2, elem1)) == 0)
                            {
                                return(NodePosition.After);
                            }
                        }
                    }
                }
            }
            if (nCompare > 0)
            {
                //elem2 > elem1
                return(NodePosition.After);
            }
            else
            {
                //elem2 < elem1
                return(NodePosition.Before);
            }
        }
コード例 #2
0
 private void SortChildren(XmlDiffElement elem)
 {
     if (elem.FirstChild != null)
     {
         XmlDiffNode _first   = elem.FirstChild;
         XmlDiffNode _current = elem.FirstChild;
         XmlDiffNode _last    = elem.LastChild;
         elem._firstChild = null;
         elem._lastChild  = null;
         //set flag to ignore child order
         bool temp = IgnoreChildOrder;
         IgnoreChildOrder = true;
         XmlDiffNode _next = null;
         do
         {
             if (_current is XmlDiffElement)
             {
                 _next = _current._next;
             }
             _current._next = null;
             InsertChild(elem, _current);
             if (_current == _last)
             {
                 break;
             }
             _current = _next;
         }while (true);
         //restore flag for ignoring child order
         IgnoreChildOrder = temp;
     }
 }
コード例 #3
0
        private void LoadElement(XmlDiffNode parent, XmlReader reader, PositionInfo pInfo)
        {
            XmlDiffElement elem          = null;
            bool           bEmptyElement = reader.IsEmptyElement;

            if (bEmptyElement)
            {
                elem = new XmlDiffEmptyElement(reader.LocalName, reader.Prefix, reader.NamespaceURI);
            }
            else
            {
                elem = new XmlDiffElement(reader.LocalName, reader.Prefix, reader.NamespaceURI);
            }
            elem.LineNumber   = pInfo.LineNumber;
            elem.LinePosition = pInfo.LinePosition;
            ReadAttributes(elem, reader, pInfo);
            if (!bEmptyElement)
            {
                //            bool rtn = reader.Read();
                //			rtn = reader.Read();
                reader.Read(); //move to child
                ReadChildNodes(elem, reader, pInfo);
            }
            InsertChild(parent, elem);
        }
コード例 #4
0
 private void ReadAttributes(XmlDiffElement parent, XmlReader reader, PositionInfo pInfo)
 {
     if (reader.MoveToFirstAttribute())
     {
         do
         {
             XmlDiffAttribute attr = new XmlDiffAttribute(reader.LocalName, reader.Prefix, reader.NamespaceURI, reader.Value);
             attr.SetValueAsQName(reader, reader.Value);
             attr.LineNumber   = pInfo.LineNumber;
             attr.LinePosition = pInfo.LinePosition;
             InsertAttribute(parent, attr);
         }while (reader.MoveToNextAttribute());
     }
 }
コード例 #5
0
        private int CompareAttributes(XmlDiffElement elem1, XmlDiffElement elem2)
        {
            int count1 = elem1.AttributeCount;
            int count2 = elem2.AttributeCount;

            if (count1 > count2)
            {
                return(1);
            }
            else if (count1 < count2)
            {
                return(-1);
            }
            else
            {
                XmlDiffAttribute current1 = elem1.FirstAttribute;
                XmlDiffAttribute current2 = elem2.FirstAttribute;
                //			NodePosition result = 0;
                int nCompare = 0;
                while (current1 != null && current2 != null && nCompare == 0)
                {
                    if ((nCompare = CompareText(current2.LocalName, current1.LocalName)) == 0)
                    {
                        if (IgnoreNS || (nCompare = CompareText(current2.NamespaceURI, current1.NamespaceURI)) == 0)
                        {
                            if (IgnorePrefix || (nCompare = CompareText(current2.Prefix, current1.Prefix)) == 0)
                            {
                                if ((nCompare = CompareText(current2.Value, current1.Value)) == 0)
                                {
                                    //do nothing!
                                }
                            }
                        }
                    }
                    current1 = (XmlDiffAttribute)current1._next;
                    current2 = (XmlDiffAttribute)current2._next;
                }
                if (nCompare > 0)
                {
                    //elem1 > attr2
                    return(1);
                }
                else
                {
                    //elem1 < elem2
                    return(-1);
                }
            }
        }
コード例 #6
0
        // This is a helper function for WriteResult.  It gets the Xml representation of the different node we wants
        // to write out and all it's children.
        private String GetNodeText(XmlDiffNode diffNode, DiffType result)
        {
            string text = string.Empty;

            switch (diffNode.NodeType)
            {
            case XmlDiffNodeType.Element:
                if (result == DiffType.SourceExtra || result == DiffType.TargetExtra)
                {
                    return(diffNode.OuterXml);
                }
                StringWriter   str      = new StringWriter();
                XmlWriter      writer   = XmlWriter.Create(str);
                XmlDiffElement diffElem = diffNode as XmlDiffElement;
                Debug.Assert(diffNode != null);
                writer.WriteStartElement(diffElem.Prefix, diffElem.LocalName, diffElem.NamespaceURI);
                XmlDiffAttribute diffAttr = diffElem.FirstAttribute;
                while (diffAttr != null)
                {
                    writer.WriteAttributeString(diffAttr.Prefix, diffAttr.LocalName, diffAttr.NamespaceURI, diffAttr.Value);
                    diffAttr = (XmlDiffAttribute)diffAttr.NextSibling;
                }
                if (diffElem is XmlDiffEmptyElement)
                {
                    writer.WriteEndElement();
                    text = str.ToString();
                }
                else
                {
                    text  = str.ToString();
                    text += ">";
                }
                writer.Dispose();
                break;

            case XmlDiffNodeType.CData:
                text = ((XmlDiffCharacterData)diffNode).Value;
                break;

            default:
                text = diffNode.OuterXml;
                break;
            }
            return(text);
        }
コード例 #7
0
 private void InsertAttribute(XmlDiffElement parent, XmlDiffAttribute newAttr)
 {
     Debug.Assert(parent != null);
     Debug.Assert(newAttr != null);
     newAttr._parent = parent;
     if (IgnoreAttributeOrder)
     {
         XmlDiffAttribute attr     = parent.FirstAttribute;
         XmlDiffAttribute prevAttr = null;
         while (attr != null && (CompareAttributes(attr, newAttr) == NodePosition.After))
         {
             prevAttr = attr;
             attr     = (XmlDiffAttribute)(attr.NextSibling);
         }
         parent.InsertAttributeAfter(prevAttr, newAttr);
     }
     else
     {
         parent.InsertAttributeAfter(parent.LastAttribute, newAttr);
     }
 }
コード例 #8
0
 private void SetElementEndPosition(XmlDiffElement elem, PositionInfo pInfo)
 {
     Debug.Assert(elem != null);
     elem.EndLineNumber   = pInfo.LineNumber;
     elem.EndLinePosition = pInfo.LinePosition;
 }
コード例 #9
0
        // This function is used to compare the attributes of an element node according to the options set by the user.
        private bool CompareAttributes(XmlDiffElement sourceElem, XmlDiffElement targetElem)
        {
            Debug.Assert(sourceElem != null);
            Debug.Assert(targetElem != null);
            if (sourceElem.AttributeCount != targetElem.AttributeCount && !IgnoreNS)
            {
                return(false);
            }

            if (sourceElem.AttributeCount == 0)
            {
                return(true);
            }

            XmlDiffAttribute sourceAttr = sourceElem.FirstAttribute;
            XmlDiffAttribute targetAttr = targetElem.FirstAttribute;

            const string xmlnsNamespace = "http://www.w3.org/2000/xmlns/";

            if (!IgnoreAttributeOrder)
            {
                while (sourceAttr != null && targetAttr != null)
                {
                    if (!IgnoreNS)
                    {
                        if (sourceAttr.NamespaceURI != targetAttr.NamespaceURI)
                        {
                            return(false);
                        }
                    }

                    if (!IgnorePrefix)
                    {
                        if (sourceAttr.Prefix != targetAttr.Prefix)
                        {
                            return(false);
                        }
                    }

                    if (sourceAttr.NamespaceURI == xmlnsNamespace && targetAttr.NamespaceURI == xmlnsNamespace)
                    {
                        if (!IgnorePrefix && (sourceAttr.LocalName != targetAttr.LocalName))
                        {
                            return(false);
                        }
                        if (!IgnoreNS && (sourceAttr.Value != targetAttr.Value))
                        {
                            return(false);
                        }
                    }
                    else
                    {
                        if (sourceAttr.LocalName != targetAttr.LocalName)
                        {
                            return(false);
                        }
                        if (sourceAttr.Value != targetAttr.Value)
                        {
                            if (ParseAttributeValuesAsQName)
                            {
                                if (sourceAttr.ValueAsQName != null)
                                {
                                    if (!sourceAttr.ValueAsQName.Equals(targetAttr.ValueAsQName))
                                    {
                                        return(false);
                                    }
                                }
                                else
                                {
                                    if (targetAttr.ValueAsQName != null)
                                    {
                                        return(false);
                                    }
                                }
                            }
                            else
                            {
                                return(false);
                            }
                        }
                    }
                    sourceAttr = (XmlDiffAttribute)(sourceAttr.NextSibling);
                    targetAttr = (XmlDiffAttribute)(targetAttr.NextSibling);
                }
            }
            else
            {
                Hashtable sourceAttributeMap = new Hashtable();
                Hashtable targetAttributeMap = new Hashtable();

                while (sourceAttr != null && targetAttr != null)
                {
                    if (IgnorePrefix && sourceAttr.NamespaceURI == xmlnsNamespace)
                    {
                        // do nothing
                    }
                    else
                    {
                        string localNameAndNamespace = sourceAttr.LocalName + "<&&>" + sourceAttr.NamespaceURI;
                        sourceAttributeMap.Add(localNameAndNamespace, sourceAttr);
                    }
                    if (IgnorePrefix && targetAttr.NamespaceURI == xmlnsNamespace)
                    {
                        // do nothing
                    }
                    else
                    {
                        string localNameAndNamespace = targetAttr.LocalName + "<&&>" + targetAttr.NamespaceURI;
                        targetAttributeMap.Add(localNameAndNamespace, targetAttr);
                    }

                    sourceAttr = (XmlDiffAttribute)(sourceAttr.NextSibling);
                    targetAttr = (XmlDiffAttribute)(targetAttr.NextSibling);
                }

                if (sourceAttributeMap.Count != targetAttributeMap.Count)
                {
                    return(false);
                }

                foreach (string sourceKey in sourceAttributeMap.Keys)
                {
                    if (!targetAttributeMap.ContainsKey(sourceKey))
                    {
                        return(false);
                    }
                    sourceAttr = (XmlDiffAttribute)sourceAttributeMap[sourceKey];
                    targetAttr = (XmlDiffAttribute)targetAttributeMap[sourceKey];

                    if (!IgnorePrefix)
                    {
                        if (sourceAttr.Prefix != targetAttr.Prefix)
                        {
                            return(false);
                        }
                    }

                    if (sourceAttr.Value != targetAttr.Value)
                    {
                        if (ParseAttributeValuesAsQName)
                        {
                            if (sourceAttr.ValueAsQName != null)
                            {
                                if (!sourceAttr.ValueAsQName.Equals(targetAttr.ValueAsQName))
                                {
                                    return(false);
                                }
                            }
                            else
                            {
                                if (targetAttr.ValueAsQName != null)
                                {
                                    return(false);
                                }
                            }
                        }
                        else
                        {
                            return(false);
                        }
                    }
                }
            }
            return(true);
        }
コード例 #10
0
        // This function compares the two nodes passed to it, depending upon the options set by the user.
        private DiffType CompareNodes(XmlDiffNode sourceNode, XmlDiffNode targetNode)
        {
            if (sourceNode.NodeType != targetNode.NodeType)
            {
                return(DiffType.NodeType);
            }
            switch (sourceNode.NodeType)
            {
            case XmlDiffNodeType.Element:
                XmlDiffElement sourceElem = sourceNode as XmlDiffElement;
                XmlDiffElement targetElem = targetNode as XmlDiffElement;
                Debug.Assert(sourceElem != null);
                Debug.Assert(targetElem != null);
                if (!IgnoreNS)
                {
                    if (sourceElem.NamespaceURI != targetElem.NamespaceURI)
                    {
                        return(DiffType.NS);
                    }
                }
                if (!IgnorePrefix)
                {
                    if (sourceElem.Prefix != targetElem.Prefix)
                    {
                        return(DiffType.Prefix);
                    }
                }

                if (sourceElem.LocalName != targetElem.LocalName)
                {
                    return(DiffType.Element);
                }
                if (!IgnoreEmptyElement)
                {
                    if ((sourceElem is XmlDiffEmptyElement) != (targetElem is XmlDiffEmptyElement))
                    {
                        return(DiffType.Element);
                    }
                }
                if (!CompareAttributes(sourceElem, targetElem))
                {
                    return(DiffType.Attribute);
                }
                break;

            case XmlDiffNodeType.Text:
            case XmlDiffNodeType.Comment:
            case XmlDiffNodeType.WS:
                XmlDiffCharacterData sourceText = sourceNode as XmlDiffCharacterData;
                XmlDiffCharacterData targetText = targetNode as XmlDiffCharacterData;
                Debug.Assert(sourceText != null);
                Debug.Assert(targetText != null);

                if (ConcatenateAdjacentTextNodes)
                {
                    DoConcatenateAdjacentTextNodes(sourceText);
                    DoConcatenateAdjacentTextNodes(targetText);
                }

                if (IgnoreWhitespace)
                {
                    if (sourceText.Value.Trim() == targetText.Value.Trim())
                    {
                        return(DiffType.Success);
                    }
                }
                else
                {
                    if (sourceText.Value == targetText.Value)
                    {
                        return(DiffType.Success);
                    }
                }
                if (sourceText.NodeType == XmlDiffNodeType.Text || sourceText.NodeType == XmlDiffNodeType.WS)     //should ws nodes also as text nodes???
                {
                    return(DiffType.Text);
                }
                else if (sourceText.NodeType == XmlDiffNodeType.Comment)
                {
                    return(DiffType.Comment);
                }
                else if (sourceText.NodeType == XmlDiffNodeType.CData)
                {
                    return(DiffType.CData);
                }
                else
                {
                    return(DiffType.None);
                }

            case XmlDiffNodeType.PI:
                XmlDiffProcessingInstruction sourcePI = sourceNode as XmlDiffProcessingInstruction;
                XmlDiffProcessingInstruction targetPI = targetNode as XmlDiffProcessingInstruction;
                Debug.Assert(sourcePI != null);
                Debug.Assert(targetPI != null);
                if (sourcePI.Name != targetPI.Name || sourcePI.Value != targetPI.Value)
                {
                    return(DiffType.PI);
                }
                break;

            default:
                break;
            }

            return(DiffType.Success);
        }
コード例 #11
0
        //  This function is being called recursively to compare the children of a certain node.
        //  When calling this function the navigator should be pointing at the parent node whose children
        //  we wants to compare and return the navigator back to the same node before exiting from it.
        private bool CompareChildren(XmlDiffNode sourceNode, XmlDiffNode targetNode)
        {
            XmlDiffNode sourceChild = sourceNode.FirstChild;
            XmlDiffNode targetChild = targetNode.FirstChild;

            bool flag     = true;
            bool tempFlag = true;

            DiffType result;

            // Loop to compare all the child elements of the parent node
            while (sourceChild != null || targetChild != null)
            {
                if (sourceChild != null)
                {
                    if (targetChild != null)
                    {
                        // Both Source and Target Read successful
                        if ((result = CompareNodes(sourceChild, targetChild)) == DiffType.Success)
                        {
                            // Child nodes compared successfully, write out the result
                            WriteResult(sourceChild, targetChild, DiffType.Success);
                            // Check whether this Node has  Children, if it does call CompareChildren recursively
                            if (sourceChild.FirstChild != null)
                            {
                                tempFlag = CompareChildren(sourceChild, targetChild);
                            }
                            else if (targetChild.FirstChild != null)
                            {
                                WriteResult(null, targetChild, DiffType.TargetExtra);
                                tempFlag = false;
                            }
                            // set the compare flag
                            flag = (flag && tempFlag);

                            // Writing out End Element to the result
                            if (sourceChild.NodeType == XmlDiffNodeType.Element && !(sourceChild is XmlDiffEmptyElement))
                            {
                                XmlDiffElement sourceElem = sourceChild as XmlDiffElement;
                                XmlDiffElement targetElem = targetChild as XmlDiffElement;
                                Debug.Assert(sourceElem != null);
                                Debug.Assert(targetElem != null);
                                if (!DontWriteMatchingNodesToOutput && !DontWriteAnythingToOutput)
                                {
                                    _Writer.WriteStartElement(String.Empty, "Node", String.Empty);
                                    _Writer.WriteAttributeString(String.Empty, "SourceLineNum", String.Empty, sourceElem.EndLineNumber.ToString());
                                    _Writer.WriteAttributeString(String.Empty, "SourceLinePos", String.Empty, sourceElem.EndLinePosition.ToString());
                                    _Writer.WriteAttributeString(String.Empty, "TargetLineNum", String.Empty, targetElem.EndLineNumber.ToString());
                                    _Writer.WriteAttributeString(String.Empty, "TargetLinePos", String.Empty, targetElem.EndLinePosition.ToString());
                                    _Writer.WriteStartElement(String.Empty, "Diff", String.Empty);
                                    _Writer.WriteEndElement();

                                    _Writer.WriteStartElement(String.Empty, "Lexical-equal", String.Empty);
                                    _Writer.WriteCData("</" + sourceElem.Name + ">");
                                    _Writer.WriteEndElement();
                                    _Writer.WriteEndElement();
                                }
                            }

                            // Move to Next child
                            sourceChild = sourceChild.NextSibling;
                            targetChild = targetChild.NextSibling;
                        }
                        else
                        {
                            // Child nodes not matched, start the recovery process
                            bool recoveryFlag = false;

                            // Try to match the source node with the target nodes at the same level
                            XmlDiffNode backupTargetChild = targetChild.NextSibling;
                            while (!recoveryFlag && backupTargetChild != null)
                            {
                                if (CompareNodes(sourceChild, backupTargetChild) == DiffType.Success)
                                {
                                    recoveryFlag = true;
                                    do
                                    {
                                        WriteResult(null, targetChild, DiffType.TargetExtra);
                                        targetChild = targetChild.NextSibling;
                                    }while (targetChild != backupTargetChild);
                                    break;
                                }
                                backupTargetChild = backupTargetChild.NextSibling;
                            }

                            // If not recovered, try to match the target node with the source nodes at the same level
                            if (!recoveryFlag)
                            {
                                XmlDiffNode backupSourceChild = sourceChild.NextSibling;
                                while (!recoveryFlag && backupSourceChild != null)
                                {
                                    if (CompareNodes(backupSourceChild, targetChild) == DiffType.Success)
                                    {
                                        recoveryFlag = true;
                                        do
                                        {
                                            WriteResult(sourceChild, null, DiffType.SourceExtra);
                                            sourceChild = sourceChild.NextSibling;
                                        }while (sourceChild != backupSourceChild);
                                        break;
                                    }
                                    backupSourceChild = backupSourceChild.NextSibling;
                                }
                            }

                            // If still not recovered, write both of them as different nodes and move on
                            if (!recoveryFlag)
                            {
                                WriteResult(sourceChild, targetChild, result);

                                // Check whether this Node has  Children, if it does call CompareChildren recursively
                                if (sourceChild.FirstChild != null)
                                {
                                    tempFlag = CompareChildren(sourceChild, targetChild);
                                }
                                else if (targetChild.FirstChild != null)
                                {
                                    WriteResult(null, targetChild, DiffType.TargetExtra);
                                    tempFlag = false;
                                }

                                // Writing out End Element to the result
                                bool bSourceNonEmpElemEnd = (sourceChild.NodeType == XmlDiffNodeType.Element && !(sourceChild is XmlDiffEmptyElement));
                                bool bTargetNonEmpElemEnd = (targetChild.NodeType == XmlDiffNodeType.Element && !(targetChild is XmlDiffEmptyElement));
                                if (bSourceNonEmpElemEnd || bTargetNonEmpElemEnd)
                                {
                                    XmlDiffElement sourceElem = sourceChild as XmlDiffElement;
                                    XmlDiffElement targetElem = targetChild as XmlDiffElement;
                                    if (!DontWriteAnythingToOutput)
                                    {
                                        _Writer.WriteStartElement(String.Empty, "Node", String.Empty);
                                        _Writer.WriteAttributeString(String.Empty, "SourceLineNum", String.Empty, (sourceElem != null) ? sourceElem.EndLineNumber.ToString() : "-1");
                                        _Writer.WriteAttributeString(String.Empty, "SourceLinePos", String.Empty, (sourceElem != null) ? sourceElem.EndLinePosition.ToString() : "-1");
                                        _Writer.WriteAttributeString(String.Empty, "TargetLineNum", String.Empty, (targetElem != null) ? targetElem.EndLineNumber.ToString() : "-1");
                                        _Writer.WriteAttributeString(String.Empty, "TargetLinePos", String.Empty, (targetElem != null) ? targetElem.EndLineNumber.ToString() : "-1");
                                        _Writer.WriteStartElement(String.Empty, "Diff", String.Empty);
                                        _Writer.WriteAttributeString(String.Empty, "DiffType", String.Empty, GetDiffType(result));
                                        if (bSourceNonEmpElemEnd)
                                        {
                                            _Writer.WriteStartElement(String.Empty, "File1", String.Empty);
                                            _Writer.WriteCData("</" + sourceElem.Name + ">");
                                            _Writer.WriteEndElement();
                                        }

                                        if (bTargetNonEmpElemEnd)
                                        {
                                            _Writer.WriteStartElement(String.Empty, "File2", String.Empty);
                                            _Writer.WriteCData("</" + targetElem.Name + ">");
                                            _Writer.WriteEndElement();
                                        }

                                        _Writer.WriteEndElement();

                                        _Writer.WriteStartElement(String.Empty, "Lexical-equal", String.Empty);
                                        _Writer.WriteEndElement();
                                        _Writer.WriteEndElement();
                                    }
                                }

                                sourceChild = sourceChild.NextSibling;
                                targetChild = targetChild.NextSibling;
                            }

                            flag = false;
                        }
                    }
                    else
                    {
                        // SourceRead NOT NULL targetRead is NULL
                        WriteResult(sourceChild, null, DiffType.SourceExtra);
                        flag        = false;
                        sourceChild = sourceChild.NextSibling;
                    }
                }
                else if (targetChild != null)
                {
                    // SourceRead is NULL and targetRead is NOT NULL
                    WriteResult(null, targetChild, DiffType.TargetExtra);
                    flag        = false;
                    targetChild = targetChild.NextSibling;
                }
                else
                {
                    //Both SourceRead and TargetRead is NULL
                    Debug.Assert(false, "Impossible Situation for comparison");
                }
            }
            return(flag);
        }