Как написать unitTest для методов, использующих поток в качестве параметра
У меня есть класс ImportProvider
, и я хочу написать unit test для метода импорта.
Но это должно быть unit test, поэтому я не хочу читать из файла в поток.
Любая идея?
public class ImportProvider : IImportProvider
{
public bool Import(Stream stream)
{
//Do import
return isImported;
}
}
public interface IImportProvider
{
bool Import(Stream input);
}
Это unit test:
[TestMethod]
public void ImportProvider_Test()
{
// Arrange
var importRepository = new Mock<IImportRepository>();
var imp = new ImportProvider(importRepository.Object);
//Do setup...
// Act
var test_Stream = ?????????????
// This working but not option:
//test_Stream = File.Open("C:/ExcelFile.xls", FileMode.Open, FileAccess.Read);
var result = imp.Import(test_Stream);
// Assert
Assert.IsTrue(result);
}
Ответы
Ответ 1
Используйте MemoryStream. Не уверен, что ожидает ваша функция, но вставляет в нее строку UTF-8, например:
//Act
using (var test_Stream = new MemoryStream(Encoding.UTF8.GetBytes("whatever")))
{
var result = imp.Import(test_Stream);
// Assert
Assert.IsTrue(result);
}
EDIT: если вам нужен файл Excel, и вы не можете читать файлы с диска, можете ли вы добавить файл Excel в качестве встроенного ресурса в тестовый проект? См. Как встраивать и получать доступ к ресурсам с помощью Visual С#
Затем вы можете читать как поток следующим образом:
//Act
using (var test_Stream = this.GetType().Assembly.GetManifestResourceStream("excelFileResource"))
{
var result = imp.Import(test_Stream);
// Assert
Assert.IsTrue(result);
}
Ответ 2
Вы можете использовать MemoryStream, чтобы обеспечить чисто поток в памяти для вашего теста.
Ответ 3
Используйте среду изоляции, такую как JustMock, TypeMock или Microsoft Fakes, и вы сможете издеваться над потоком.
Плохая новость в том, что все они, насколько мне известно, оплачиваются.
Ответ 4
Мое решение состоит в том, чтобы обернуть Stream
в свой собственный класс, назовите его StreamWrapper
, который реализует интерфейс IStream
. Теперь измените подпись импорта на
public bool Import(IStream stream)
Теперь вы можете издеваться над этим потоком, и если вы хотите использовать его в производственном коде, вы должны передать StreamWrapper
в противном случае Mock.