javascript - 开 Jest - 在描述 block 中导入多个测试,重用 beforeEach() 中定义的变量

标签 javascript automated-tests jestjs

我熟悉 RSpec,通过编写共享示例很容易重用测试用例

shared_example_for 'a cute pet' do 
  it 'tests that the pet is a small' { expect(pet.size).to be_lesser_than(10) }
  it 'tests that the pet can smile' { expect(pet.can_smile?).to be }
end

describe 'The Octocat' do
  let(:pet) { Octocat.new }

  it_behaves_like 'a cute pet'
end
...
describe 'The Doge' do 
  let(:pet) { Doge.new }

  it_behaves_like 'a cute pet'
end
Jest 中是否有等价物?可以让我重用在 beforeEach() block 中设置的变量吗?我正在尝试使用以下方法找到一种方法:
# __tests__/cuteness.js
export const cutenessTests = function() {
  test('it is small', () => {
    expect(petSetInBefore.length).toBeLesserThan(5)
  })
  test('it can smile', () => {
    expect(petSetInBefore.canSmile).toBe(true)
  })
}

# __tests__/famous_animals.test.js
import { cutenessTests } from './cuteness'

describe('Famous animals', () => {
  let petSetInBefore;

  describe('Octocat', () => {
    beforeEach(() => {
      petSetInBefore = new Octocat();
    })

    cutenessTests.bind(this)()
  })
})

这里重要的是我正在尝试共享多个 test定义而不仅仅是一个,否则我可以将 petSetInBefore 传递给共享函数。
编辑:我的每个测试和嵌套描述都可能改变我的测试环境和对象,因此 beforeEach 用于恢复正确的测试环境。这是一个更好的例子
class Octocat {
  get strokeFor(time) {
    this.strokeTime = this.strokeTime + time
    if (this.strokeTime <= 10) {
      this.mood = 'happy'
    } else {
      this.mood = 'bored'
    }
  }
}

class Doge {
  get strokeFor(time) {
    this.strokeTime = this.strokeTime + time
    if (this.strokeTime <= 5) {
      this.mood = 'happy'
    } else {
      this.mood = 'bored'
    }
  }
}

const cutenessTests = function() {
  describe('when stroked for a short while', () => {
    beforeEach(() => {
      petSetInBefore.strokeFor(1);
    })

    test('it is happy', () => { expect(petSetInBefore.mood).to(eq('happy')) }

    describe('when stroked too much', () => {
      beforeEach(() => {
        petSetInBefore.stroke(1000);
      })

      test('it gets bored', () => { expect(petSetInBefore.mood).to(eq('bored')) }
    })

    describe('when stroked a little longer', () => {
      beforeEach(() => {
        petSetInBefore.strokeFor(4);
      })

      test('it is still happy', () => { expect(petSetInBefore.mood).to(eq('happy')) }
    })
  })
}
EDIT2:这是一个 repl.it基于 Gui3's answer
EDIT3:可以在可重用测试之前或期间更改对象
describe('Famous animals', () => {
  let petSetInBefore;

  describe('Octocat', () => {
    beforeEach(() => {
      petSetInBefore = new Octocat();
    })

    describe('when it is not well rested', () => { 
      beforeEach(() => { petSetInBefore.wellRested() } // Extra object preparation / context before calling reusable examples
      cutenessTests()
    }),
    describe('when it is not well rested', () => { 
      // Calling reusable examples without extra context
      cutenessTests()
    })
  })
})

最佳答案

开 Jest 有 describe.each(table) 我没有看到它被大量使用,但它对于重用具有共同/相同结果的测试非常有帮助。

如果对两个测试对象的期望相同,您可以这样做:

const aCutePet = pet => {
  it("should be small", () => {
    expect(pet.size).toBeLessThan(10);
  });

  it(`should be able to smile`, () => {
    expect(pet).toHaveProperty('can_smile', true)
  });
}

describe.each([
  [new Doge],
  [new Octocat]
])("The %O", aCutePet);

输出:
  The Doge { size: 3, can_smile: true }
    ✓ should be small (1ms)
    ✓ should be able to smile (1ms)
  The Octocat { size: 5, can_smile: true }
    ✓ should be small
    ✓ should be able to smile (1ms)

关于javascript - 开 Jest - 在描述 block 中导入多个测试,重用 beforeEach() 中定义的变量,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/51932183/

相关文章:

node.js - 服务器实例, Jest 和 'listen EADDRINUSE:::3000'

javascript - 从下拉列表中选择后触发更改事件

javascript - 滑动手指时 ionic 变形屏幕

javascript - jQuery 隐藏所有而不是只隐藏不活动

javascript - Mocha.js 测试 bail(false) 不适用于 beforeEach

javascript - 使用 Material UI 和 React 测试库时从对话框测试 onClose 回调?

reactjs - useEffect 内部的函数调用未在 Jest 测试中触发

javascript - 在没有监听器的情况下将消息从 background.js 发送到 popup.js

unit-testing - 测试测试?

docker - 我怎样才能弄清楚为什么 Docker 中的 testcafe 这么慢