Reputation: 34305
I'm at a loss for how to even begin creating unit tests for this method:
public override void ModifyXmlDocument(Foo foo, string nodeToChange, string newValue)
{
XmlDocument xmlDocument = new XmlDocument();
xmlDocument.Load(foo.XmlPathAndFileName);
XmlElement rootElement = xmlDocument.DocumentElement;
// rest of method (to modify an XML doc) here
}
That method simply finds the element/node in an XML doc and updates it with the user-supplied value. (The method is more complex than what is shown here.)
The part that I'm having a hard time with is understanding how to have this method execute, without relying on the hard disk. But xmlDocument.Load()
takes a file path and loads a file from disk. At the end of the method, it saves the updated file back to disk.
How can I make this method unit testable?
Upvotes: 1
Views: 2311
Reputation: 67115
There are a couple of ways you can do this, but all require a refactoring of your code. ModifyXmlDocument
will need to take XmlDocument
as a parameter, then you can mock it from there on.
public void test_that_xml_is_loaded()
{
var sut = new SUT();
var xmldocumentfake = new Mock<XmlDocument>(){CallBase=true};
xmldocumentfake.Setup(x=>x.LoadXml(It.IsAny<String>()));
sut.ModifyXmlDocument(foo, nodeToChange, newValue, xmlDocumentfake.Object);
xmldocumentfake.Verify(x=>x.LoadXml(It.IsAny<String>()), Times.Once());
}
You could also wrap the XmlDocument
in another class that you can write as an abstraction that can be modified. Again, you would have to pass it in, though.
Also, as Anthony Pegram had alluded and what I mean: be careful that you are not breaking the Single Responsibility Principle. When tests are too hard to write, that is often a scream that you have broken that principle.
Upvotes: 6
Reputation: 6152
A couple of options:
Upvotes: 1