我試圖單元測試一個方法,並且它使用傳遞給模擬方法的字典向電子郵件添加附件。測試總是失敗,通過一切似乎是正確的,但Assert
似乎沒有驗證。用xunit檢查字典<字符串,流>
是否有一種特殊的單元測試字典的方式,一般來說,它的工作原理是設置爲<string, Stream>
。代碼在下面,但不要認爲它與任何東西有關,但可能已經錯誤地設置了一些東西,我想我錯過了一些明顯的東西。
[Fact]
public void Process_ShouldAttachCsvStreamWhenBuildingEmailMessage()
{
//Arrange
var fixture = new Fixture();
var settings = fixture.Create<Settings>();
var sutFixtures = new SUTFixtures(true);
var response = RemoteClientResponseHelper.GetMockHttpWebResponse(sutFixtures.Items);
//deal with attachement
var csv = sutFixtures.ToCsv();
var bytes = Encoding.GetEncoding("iso-8859-1").GetBytes(csv);
var messageAttachments = new Dictionary<string, Stream> {{"MissingImages.csv", new MemoryStream(bytes)}};
var moqClientService = new Mock<IClientService>();
moqClientService.Setup(x => x.Call(It.IsAny<string>(), It.IsAny<string>(), It.IsAny<string>(), It.IsAny<string>(), null))
.Returns(response.Object);
Dictionary<string, Stream> attachmentsVerify = null;
var moqEmailService = new Mock<IEmailService>();
moqEmailService.Setup(
x =>
x.BuildMessage(It.IsAny<string>(), It.IsAny<string>(), It.IsAny<string>(), It.IsAny<string>(),
It.IsAny<bool>(), It.IsAny<Dictionary<string, Stream>>()))
.Callback<string, string, string, string, bool, Dictionary<string, Stream>>(
(to, from, subject, body, isHtml, attachments) =>
{
attachmentsVerify = attachments;
});
//Act
var sut = new MissingImageNotificationStep(moqClientService.Object, moqEmailService.Object, settings);
sut.Process(new MappingData() { Parts = sutFixtures.DataTable });
//Assert
moqEmailService.Verify(m => m.BuildMessage(It.IsAny<string>(),
It.IsAny<string>(),
It.IsAny<string>(),
It.IsAny<string>(),
It.IsAny<bool>(),
It.IsAny<Dictionary<string, Stream>>()), Times.Once());
Assert.Equal(messageAttachments, attachmentsVerify);
}
UPDATE,我想過一個自定義比較,但也許認爲這是已經存在的東西
一定很懶惰。我有一些工作,無論如何,我的情況下,看着比較器我必須做一些明確的鑄造這是罰款在我的情況,但有點臭,因此我的代碼需要重構,也不知道GetHash在這種情況下做任何事情,如果這個代碼在測試之外使用,我會看看。
自定義比較
public class DictionaryComparer : IEqualityComparer<Dictionary<string, Stream>>
{
private readonly IEqualityComparer<Stream> _valueComparer;
public DictionaryComparer(IEqualityComparer<Stream> valueComparer = null)
{
this._valueComparer = valueComparer ?? EqualityComparer<Stream>.Default;
}
public bool Equals(Dictionary<string, Stream> x, Dictionary<string, Stream> y)
{
if (x.Count != y.Count)
return false;
if (x.Keys.Except(y.Keys).Any())
return false;
if (y.Keys.Except(x.Keys).Any())
return false;
foreach (var pair in x)
{
var xValue = pair.Value as MemoryStream;
var yValue = y[pair.Key] as MemoryStream;
if (xValue.Length != yValue.Length)
return false;
xValue.Position = 0;
yValue.Position = 0;
var xArray = xValue.ToArray();
var yArray = yValue.ToArray();
return xArray.SequenceEqual(yArray);
}
return true;
}
public int GetHashCode(Dictionary<string, Stream> obj)
{
unchecked
{
var hash = 17;
foreach (var key in obj.Keys)
{
hash = hash * 23 + key.GetHashCode();
}
return hash;
}
}
}
通過的xUnit
Assert.Equal(messageAttachments, attachmentsVerify, new DictionaryComparer());
您是否考慮重寫Dictionary上的Equal方法? –