Dot-Net

您如何對內部使用計時器的類進行單元測試?

  • July 2, 2009

不管你喜不喜歡,有時你必須為在內部使用定時器的類編寫測試。

例如,一個類會報告系統可用性並在系統停機時間過長時引發事件

public class SystemAvailabilityMonitor {
   public event Action SystemBecameUnavailable = delegate { };
   public event Action SystemBecameAvailable = delegate { };
   public void SystemUnavailable() {
       //..
   }
   public void SystemAvailable() {
       //..
   }
   public SystemAvailabilityMonitor(TimeSpan bufferBeforeRaisingEvent) {
       //..
   }
}

我有一些我使用的技巧(將這些技巧作為答案發布)但我想知道其他人會做什麼,因為我對我的任何一種方法都不完全滿意。

我從對警報做出反應的對像中提取計時器。例如,在 Java 中,您可以將 ScheduledExecutorService 傳遞給它。在單元測試中,我通過了一個我可以確定性控制的實現,例如jMock 的 DeterministicScheduler

如果你正在尋找這個問題的答案,你可能會對這個部落格感興趣: http: //thorstenlorenz.blogspot.com/2009/07/mocking-timer.html

在其中我解釋了一種方法來覆蓋 System.Timers.Timer 類的通常行為,使其在 Start() 上觸發。

這是簡短的版本:

class FireOnStartTimer : System.Timers.Timer
{
public new event System.Timers.ElapsedEventHandler Elapsed;

public new void Start()
{
 this.Elapsed.Invoke(this, new EventArgs() as System.Timers.ElapsedEventArgs);
}
}

當然,這要求您能夠將計時器傳遞給被測類。如果這是不可能的,那麼類的設計在可測試性方面存在缺陷,因為它不支持依賴注入。如果可以的話,你應該改變它的設計。否則,您可能會不走運,並且無法測試該類涉及其內部計時器的任何內容。

有關更詳盡的解釋,請訪問部落格。

引用自:https://stackoverflow.com/questions/879971