我在ASP.NET核心中有一个类,它使用Threading.Timer在给定的时间间隔内运行一个小任务(因为在Core中没有Timer.Timer)。现在我编写了一个单元测试,用于检查作业运行的时间:
[Fact]
public async void IntervalExecutionTest()
{
var target = new PeriodicaBackgroundJobRunner();
var testJob = new PeriodicalJobForTest();
target.Start(1/*run every second*/, testJob);
await Task.Delay(2500).ContinueWith(c =>
{
Assert.Equal(3, testJob.ExecutedCounter);
});
}
测试工作如下:
private class PeriodicalJobForTest : IPeriodicalJob
{
public int ExecutedCounter { get; private set; }
public void Execute(object state)
{
this.ExecutedCounter++;
}
}
因此,等待时间为2.5秒,我预计它会在0,1和2上运行3次。
在调试测试过程中。然而,构建服务器失败并说“预期3,实际1”。
为什么?有什么不同?一旦它实际部署到Azure,我是否也会在生产中遇到问题?
注意:我也尝试过使用Thread.Sleep(),结果相同。
如果问题实际上可能与测试实现中的类有关,那么该类看起来像这样:
public class PeriodicaBackgroundJobRunner : IPeriodicaBackgroundJobRunner
{
private Threading.Timer timer;
public void Start(int interval, IPeriodicalJob job)
{
interval = Math.Max(interval, 1) * 1000;
if (this.timer == null)
{
this.timer = new Timer(new TimerCallback(job.Execute), null, Timeout.Infinite, interval);
}
this.timer.Change(0, interval);
}
public void Stop()
{
if (this.timer != null)
{
this.timer.Change(Timeout.Infinite, Timeout.Infinite);
}
}
}
答案 0 :(得分:0)
嗯,不确定问题究竟是什么,但它与Threading.Timer有关。当我在没有计时器的情况下重写课程时,测试工作正常:
public class PeriodicaBackgroundJobRunner : IPeriodicaBackgroundJobRunner
{
private CancellationTokenSource cancellationToken;
public void Start(int interval, IPeriodicalJob job)
{
Task.Run(async () =>
{
interval = Math.Max(interval, 1) * 1000;
this.cancellationToken = new CancellationTokenSource();
while (true)
{
job.Execute(null);
await Task.Delay(interval, this.cancellationToken.Token);
}
});
}
public void Stop()
{
if (this.cancellationToken != null)
{
this.cancellationToken.Cancel();
}
}
}