Angular2使用fakeAsync测试被拒绝的承诺

时间:2016-10-02 16:07:07

标签: angular jasmine

我试图测试我已经建立的服务,它在幕后做了一些异步工作。请记住,我正在使用立即解析承诺的模拟,因此实际上不会发生真正的异步工作。

我的测试看起来像这样:

it('should reject promise when condition is met',
  inject([MyService], fakeAsync((myService: MyService) => {
    let rejected = false;

    myService.doSomeAsyncWork().catch(() => {
      rejected = true;
    });
    tick();

    expect(rejected).toBe(true);
  }))
);

当我运行时,我收到以下错误:

Error: 2 timer(s) still in the queue.

如果我将tick()更改为tick(1000),那么它告诉我只有1个计时器仍然在队列中。如果我多次调用tick(),那就不会有任何区别。

我做错了什么?

谢谢!

2 个答案:

答案 0 :(得分:1)

我最终为此删除了fakeAsync,只使用了经典的“done()”方法:

it('should reject promise when condition is met', done => {
  let rejected: boolean;

  myService.doSomeAsyncWork().then(() => {
    rejected = false;
  }, () => {
    rejected = true;
  }).then(() => {
    expect(rejected).toBe(true);
    done();
  });
});

答案 1 :(得分:0)

当在fakeAsync区域中运行测试时,我们可以使用两个函数flushMicrotasks和tick。 tick函数将时间提前指定的毫秒数,因此tick(100)将执行100ms内发生的所有异步任务。 flushMicrotasks函数将清除队列中当前存在的所有微任务。简而言之,如果您不确定时间或依赖于promise / settimeout,则需要使用flush()方法。

因此,在您的情况下:flush()将解决此问题。

it('should reject promise when condition is met',
inject([MyService], fakeAsync((myService: MyService) => {
let rejected = false;

myService.doSomeAsyncWork().catch(() => {
  rejected = true;
});
flush();  // changed tick to flush() 

expect(rejected).toBe(true);

})) );