node.js - clearTimeout 测试不适用于 jest.useFakeTimers()

标签 node.js typescript unit-testing jestjs ts-jest

我正在尝试迁移到 jest.useFakeTimers() 的“现代”版本,这不是版本 27.x 中的默认值。
我的测试有一些问题,因为 Jest 一直在说像 clearTimeoutsetInterval 这样的函数不是 Jest 模拟:

// Poster.ts
// This is the class method I'm testing

startInterval(interval = 1800000) {
  this._interval && clearTimeout(this._interval)

  this._interval = (setInterval(
    () =>
      this.post()
        .then((result) => {
          this.runHandlers('autopostSuccess', result)
          return result
        })
        .catch((error) => this.runHandlers('autopostFail', error)),
    interval
  ) as unknown) as number
  return this._interval
}
// Poster.test.ts
describe('startInterval method', () => {
  const p = new Poster({ client: {} })
  beforeEach(() => {
    jest.useFakeTimers()
  })
  afterEach(() => {
    jest.useRealTimers()
  })

  it('should call clearTimeout (but only from the second use)', () => {
    const firstID = p.startInterval()
    expect(clearTimeout).not.toHaveBeenCalled() // This line fails with the following error
    p.startInterval()
    expect(clearTimeout).toHaveBeenCalledTimes(1)
    expect(clearTimeout).toHaveBeenLastCalledWith(firstID)
  })

  // ...
})

错误:

expect(received).not.toHaveBeenCalled()

Matcher error: received value must be a mock or spy function

因此,它提示 clearTimeout 不是模拟,即使我使用的是 jest.useFakeTimers()

版本:

  • 开 Jest @ 27.0.3
  • ts-jest @ 27.0.2
  • typescript @ 4.2.4
  • Node @12.14.0

我确定我在这里遗漏了一些东西,也许我以错误的方式使用了 useFakeTimers,但 method docs 都不是也不是 page on Timer Mocks对我有帮助。

有人知道为什么我的测试不起作用吗?

最佳答案

经过一番挖掘后,我很有希望找到了正确的方法。

答案就在这个issue讨论。

Jest added spies to the fake timers automatically. We no longer do that, people need to do e.g. jest.spyOn(global, 'setTimeout') themselves.

这对我有用。只需添加 jest.spyOn(global, 'clearTimeout') 就可以了。也许您甚至不需要 jest.useFakeTimers() 语句。

关于node.js - clearTimeout 测试不适用于 jest.useFakeTimers(),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/67770314/

相关文章:

javascript - (Koa.js) 生成器和产量基础知识

向数据库插入行时 MySQL 语法错误

node.js - 配置node.js聊天

javascript - 如何将数据从选定的选项发送到组件

javascript - 在 typescript 中,如何实现带有回调的接口(interface)?

javascript - 如何在express中为静态文件设置动态路由

typescript - 如何在不求助于 'any' 的情况下键入此函数

ios - PromiseKit 没有回调/解除分配? (阿拉莫菲尔)

javascript - 如何使用 Chai 测试函数的返回值

unit-testing - Ember Controller 上的单元测试计算属性