对时间增量进行单元测试
我想对以下方法进行单元测试:
public void Upload(string identifier, Stream data)
{
var startTime = SystemTime.Now;
innerDataIntegrationInterface.Upload(identifier, data);
var endTime = SystemTime.Now;
TimeSpan totalUploadTime = endTime.Subtract(startTime);
float transferRate = data.Length / (float)(totalUploadTime.Seconds + totalUploadTime.Milliseconds);
m_log.Info(string.Format("Total uploading time for '{0}' was {1:00}.{2:000000} milliseconds transfered at {3} bytes/sec", identifier, totalUploadTime.Seconds, totalUploadTime.Milliseconds, transferRate));
}
基本上我已经注入了 SystemTime 对象,因此我可以在测试中设置它,但我不知道该怎么做才能使 startTime 和 endTime 变量获得不同的值所以我可以断言 m_log.Info 方法被调用时使用了totalUploadTime 和transferRate 变量的正确值。
任何想法将不胜感激。
I have the following method that I would like to unit test:
public void Upload(string identifier, Stream data)
{
var startTime = SystemTime.Now;
innerDataIntegrationInterface.Upload(identifier, data);
var endTime = SystemTime.Now;
TimeSpan totalUploadTime = endTime.Subtract(startTime);
float transferRate = data.Length / (float)(totalUploadTime.Seconds + totalUploadTime.Milliseconds);
m_log.Info(string.Format("Total uploading time for '{0}' was {1:00}.{2:000000} milliseconds transfered at {3} bytes/sec", identifier, totalUploadTime.Seconds, totalUploadTime.Milliseconds, transferRate));
}
Basically I am already injecting the SystemTime object so I can set it up in my test but I can't figure out what to do so that the startTime and endTime variables get different values so I can assert that the m_log.Info method gets called with the correct values for the totalUploadTime and transferRate variables.
Any ideas would be appreciated.
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(4)
时钟的概念 - 可以获取当前时间的东西 - 实际上是您所依赖的服务。如果您像任何其他服务一样通过某个接口(
IClock
)明确依赖它。然后,您可以创建一个委托给 System.DateTime.UtcNow 或 System.DateTime.Now 的“生产”实现以及用于测试的伪实现或模拟。就我个人的经验而言,值得拥有一个可以设置、提前等的假冒,而不是在这个特定场景中使用模拟框架 - 这是我自己经常看到和使用的一种技术(这就是为什么 Noda Time 通过
IClock
接口和一个StubClock
实施)。The idea of a clock - something can get the current time - is effectively a service you're depending on. If you depend on it explicitly via some interface (
IClock
) like you would any other service. You can then create a "production" implementation which delegates toSystem.DateTime.UtcNow
orSystem.DateTime.Now
and a fake implementation or a mock for testing.Personally in my experience it's worth having a fake that you can set, advance etc rather than using a mock framework for this particular scenario - it's a technique I've seen and used myself quite a bit (which is why Noda Time supports it with the
IClock
interface and aStubClock
implementation).您可以让您的模拟
SystemTime
对象在Now
Getter 中增加它的值吗?这会让他们与众不同。Can you make your Mock
SystemTime
object increment it's value in theNow
Getter? That would make them different.如果
innerDataIntegrationInterface.Upload
是模拟接口的一部分,您可以模拟Upload
方法,如下所示:上面是在 C# 中使用 Moq
If
innerDataIntegrationInterface.Upload
is a part of mocked interface you can mock theUpload
method like:The above is in c# using Moq
处理此问题的一种方法是将代码的复杂部分(您真正想要测试的部分)提取到另一个类或方法中并进行测试。
在这种情况下,这将涉及将计算传输速率的逻辑提取到一个单独的方法中,该方法采用两个时间参数和传输量。
(又名“收集,然后使用”来自 Mock-消除模式。)
One way to handle this is to extract the complicated part of your code (the portion you really want to test) into another class or method and test that.
In this case, that would involve extracting the logic to calculate the transfer rate into a separate method that takes two time parameters and the amount transferred.
(aka, "Gather, Then Use" from Mock-Eliminating Patterns.)