What is the best way to compare XML files for equality?

15,431

Solution 1

It really depends on what you want to check as "differences".

Right now, we're using Microsoft XmlDiff: http://msdn.microsoft.com/en-us/library/aa302294.aspx

Solution 2

You might find it's less fragile to parse the XML into an XmlDocument and base your Assert calls on XPath Query. Here are some helper assertion methods that I use frequently. Each one takes a XPathNavigator, which you can obtain by calling CreateNavigator() on the XmlDocument or on any node retrieved from the document. An example of usage would be:

     XmlDocument doc = new XmlDocument( "Testdoc.xml" );
     XPathNavigator nav = doc.CreateNavigator();
     AssertNodeValue( nav, "/root/foo", "foo_val" );
     AssertNodeCount( nav, "/root/bar", 6 )

    private static void AssertNodeValue(XPathNavigator nav,
                                         string xpath, string expected_val)
    {
        XPathNavigator node = nav.SelectSingleNode(xpath, nav);
        Assert.IsNotNull(node, "Node '{0}' not found", xpath);
        Assert.AreEqual( expected_val, node.Value );
    }

    private static void AssertNodeExists(XPathNavigator nav,
                                         string xpath)
    {
        XPathNavigator node = nav.SelectSingleNode(xpath, nav);
        Assert.IsNotNull(node, "Node '{0}' not found", xpath);
    }

    private static void AssertNodeDoesNotExist(XPathNavigator nav,
                                         string xpath)
    {
        XPathNavigator node = nav.SelectSingleNode(xpath, nav);
        Assert.IsNull(node, "Node '{0}' found when it should not exist", xpath);
    }

    private static void AssertNodeCount(XPathNavigator nav, string xpath, int count)
    {
        XPathNodeIterator nodes = nav.Select( xpath, nav );
        Assert.That( nodes.Count, Is.EqualTo( count ) );
    }

Solution 3

I wrote a small library with asserts for serialization, source.

Sample:

[Test]
public void Foo()
{
   ...
   XmlAssert.Equal(expected, actual, XmlAssertOptions.IgnoreDeclaration | XmlAssertOptions.IgnoreNamespaces);
}

NuGet

Share:
15,431
Scott Lawrence
Author by

Scott Lawrence

I lead a small team within Capital One implementing fraud defenses within the agent servicing platform, among other enhancements. I occasionally blog here: http://scottlaw.knot.org/blog/ on technology and my other interests. My technology career to-date has spanned many roles beyond hands-on software engineer, including systems analyst, project manager, scrum master, database administrator, and team lead for previous employers. I earned degrees in computer science (BSc) and business (MBA) at the University of Maryland-College Park.

Updated on June 05, 2022

Comments

  • Scott Lawrence
    Scott Lawrence about 2 years

    I'm using .NET 2.0, and a recent code change has invalidated my previous Assert.AreEqual call (which compared two strings of XML). Only one element of the XML is actually different in the new codebase, so my hope is that a comparison of all the other elements will give me the result I want. The comparison needs to be done programmatically, since it's part of a unit test.

    At first, I was considering using a couple instances of XmlDocument. But then I found this: http://drowningintechnicaldebt.com/blogs/scottroycraft/archive/2007/05/06/comparing-xml-files.aspx

    It looks like it might work, but I was interested in Stack Overflow feedback in case there's a better way.

    I'd like to avoid adding another dependency for this if at all possible.

    Similar questions

  • Scott Lawrence
    Scott Lawrence over 15 years
    I came across this link via the blog post I linked to in the question. I was hoping to avoid adding another dependency, if at all possible.
  • Scott Lawrence
    Scott Lawrence over 15 years
    Thanks Jeremy, this looks like a good solution. I'll try it out.
  • Filini
    Filini over 15 years
    Then I guess you have to decide what's a "difference" for you, and develop your own algorythm with XmlDocuments, XpathNavigators, etc... But I think you are looking for a "business difference", not an "xml difference"
  • Scott Lawrence
    Scott Lawrence over 15 years
    In this case, I know the structure between the two documents will be the same (no missing or extra elements). It's just whether the values of elements are the same or not.