【发布时间】:2016-03-25 20:47:31
【问题描述】:
为了帮助进行单元测试,我们将DateTime 类封装在一个委托中,以便可以在单元测试中覆盖DateTime.Now。
public static class SystemTime
{
#region Static Fields
public static Func<DateTime> Now = () => DateTime.Now;
#endregion
}
这是一个在 xunit 单元测试中使用的示例:
[Fact]
public void it_should_update_the_last_accessed_timestamp_on_an_entry()
{
// Arrange
var service = this.CreateClassUnderTest();
var expectedTimestamp = SystemTime.Now();
SystemTime.Now = () => expectedTimestamp;
// Act
service.UpdateLastAccessedTimestamp(this._testEntry);
// Assert
Assert.Equal(expectedTimestamp, this._testEntry.LastAccessedOn);
}
测试在本地运行良好,但在我们的构建服务器上失败,因为Assert 语句中的日期时间不同。
鉴于DateTime 是通过上述委托包装器模拟的,我很难想出它失败的原因。我已验证 UpdateLastAccessedTimestamp 方法的实现没有问题,并且测试在本地运行时通过。
很遗憾,我无法在我们的构建服务器上调试它。任何想法为什么它只会在构建服务器上运行时失败?
注意UpdateLastAccessedTimestamp的实现如下:
public void UpdateLastAccessedTimestamp(Entry entry)
{
entry.LastAccessedOn = SystemTime.Now();
this._unitOfWork.Entries.Update(entry);
this._unitOfWork.Save();
}
Entry 类只是一个简单的 POCO 类,它有许多字段,包括 LastAccessedOn 字段:
public class Entry
{
public DateTime LastAccessedOn { get; set; }
//other fields that have left out to keep the example concise
}
【问题讨论】:
-
UpdateLastAccessedTimestamp是否进行任何日期操作,或者可能从外部来源获取时间?你能看到expected和actual之间的失败原因(values)吗? this._testEntry 是什么?您的Act部分似乎没有传入您的预期时间戳 -
@Kritner 感谢您的回复。我已根据您的反馈更新了我的问题。请注意,对 _unitOfWork 对象的调用不会对 LastAccessedOn 字段进行任何操作。
-
只是好奇...如果你用
SystemTime.Now = () => expectedTimestamp;代替SystemTime.Now = () => new DateTime(2000, 1, 1);- 你的结果会是什么?您的预期是 2000、1、1 吗?你的实际是 2000、1、1 吗?还是可能是 2016 年 2 月 24 日?希望这至少有助于缩小问题所在。 -
你能分享
CreateClassUnderTest和_testEntry吗?
标签: c# unit-testing datetime nunit xunit