我目前正在尝试学习正确的单元测试。所以现在我正在尝试为一个类编写单元测试,该类应该将XML-File中的数据映射到正确的对象。当然,该类的所有功能都取决于相应XML文件的存在。 XML文件加载在类的构造函数中。
我正在使用C#和NUnit。到目前为止,我有两个测试:
[Test]
public void ShouldAllowInstanceToBeCreatedWhenXMLFileIsPresent()
{
if (File.Exists(SettingsReader.XML_SETTINGS_PATH))
{
SettingsReader settingsReader = new SettingsReader();
Assert.AreNotEqual(null, settingsReader);
}
}
[Test]
[ExpectedException("Telekanzlei.Clientmanager.XMLDataLayer.XMLFileNotFoundException")]
public void ShouldThrowExceptionWhenXMLFileIsNotPresent()
{
if (!File.Exists(SettingsReader.XML_SETTINGS_PATH))
{
SettingsReader settingsReader = new SettingsReader();
}
else
throw new XMLFileNotFoundException();
}
我不确定在测试中检查文件是否存在是正确的方法,所以对这些测试的任何建议也是受欢迎的。但我的问题是,如何进行以下测试。如果XML文件不存在,显然所有后续测试都将失败。
因此,我认为XML文件存在,同时请记住,失败的测试只是意味着它不是吗?这对我来说似乎不对。
是否有一般模式来处理这样的问题?
获取任何帮助
编辑:重新编写第二个测试,因为如果文件实际存在则失败...
edit2:可能有助于告诉你,SettingsReader实际上做了什么。到目前为止它看起来像这样:
public class SettingsReader
{
public static readonly string XML_SETTINGS_PATH = "C:\\Telekanzlei\\Clientmanager_2.0\\Settings.xml";
public XElement RootXElement { get; private set; }
public SettingsReader()
{
if (!File.Exists(XML_SETTINGS_PATH))
throw new XMLFileNotFoundException();
using (var fs = File.OpenRead(XML_SETTINGS_PATH))
{
RootXElement = XElement.Load(fs);
}
}
}
我不确定,但我猜一个StreamReader不会是去这里的方式,不是吗?
答案 0 :(得分:14)
问题不在于您的单元测试,而在于课程的设计。我建议重构该类,以便它不会打开文件,而是在流上运行。然后你的单元测试可以简单地替换内存流的文件流 - 简单! :)
public class SettingsReader()
{
public SettingsReader(System.IO.StreamReader reader)
{
// read contents of stream...
}
}
// In production code:
new SettingsReader(new StreamReader(File.Open("settings.xml")));
// In unit test:
new SettingsReader(new StringReader("<settings>dummy settings</settings>"));
请记住,打开文件并解析设置数据是两个非常不同的问题。
答案 1 :(得分:5)
如果您必须建议您使用 SetUp 方法来复制或验证该文件是否存在。 我建议通过将文件添加到测试项目并将其标记为&#34;始终复制&#34;来确保文件存在。一旦你开始工作就没有必要重新检查它 如果你有很多需要外部文件的测试,你可能应该使用MsTest - 它有一个名为 DeploymentItem 的属性,可以确保将文件复制到与测试相同的位置。
答案 2 :(得分:3)
考虑重写代码,以便可以传入依赖关系,或以其他方式存储您想要进行单元测试的代码。
即。将类似“IMySettingsFileProvider”实例的内容传递给SettingsReader构造函数,其中IMySettingsFileProvider.SettingsXml返回一些设置流。这样,您可以模拟IMySettingsFileProvider接口进行测试,而不是要求文件存在于磁盘上。
答案 3 :(得分:1)
一种选择是将它放在测试夹具的顶部。然后测试仅在文件存在时才有效。
[SetUp]
public void Setup()
{
Assume.That(File.Exists(SettingsReader.XML_SETTINGS_PATH));
}