React 16 Jest ES6 Class Mocks(使用ES6語法類的模擬) 實例三、四

轉(zhuǎn)載地址

React 16 Jest ES6 Class Mocks(使用ES6語法類的模擬) 實例三、四

項目初始化

git clone https://github.com/durban89/webpack4-react16-reactrouter-demo.git 
cd webpack4-react16-reactrouter-demo
git fetch origin
git checkout v_1.0.31
npm install

ES6 Class Mocks(使用ES6語法類的模擬)

Jest可用于模擬導入到要測試的文件中的ES6語法的類。

ES6語法的類是具有一些語法糖的構(gòu)造函數(shù)。因此,ES6語法的類的任何模擬都必須是函數(shù)或?qū)嶋H的ES6語法的類(這也是另一個函數(shù))。
所以可以使用模擬函數(shù)來模擬它們。如下

ES6語法類的實例

這里的實例我使用官方的例子,SoundPlayer類和SoundPlayerConsumer消費者類。下面部分文件的內(nèi)容參考上篇文章React 16 Jest ES6 Class Mocks(使用ES6語法類的模擬)src/lib/sound-player.js

export default class SoundPlayer {
  constructor() {
    this.name = 'Player1';
    this.fileName = '';
  }

  choicePlaySoundFile(fileName) {
    this.fileName = fileName;
  }

  playSoundFile() {
    console.log('播放的文件是:', this.fileName);
  }
}

src/lib/sound-player-consumer.js

import SoundPlayer from './sound-player';

export default class SoundPlayerConsumer {
  constructor() {
    this.soundPlayer = new SoundPlayer();
  }

  play() {
    const coolSoundFileName = 'song.mp3';
    this.soundPlayer.choicePlaySoundFile(coolSoundFileName);
    this.soundPlayer.playSoundFile();
  }
}

ES6語法的類測試實例三 - 使用模塊工廠參數(shù)調(diào)用jest.mock()(Calling jest.mock() with the module factory parameter)jest.mock(path,moduleFactory)接受模塊工廠參數(shù)。

模塊工廠是一個返回模擬的函數(shù)。
為了模擬構(gòu)造函數(shù),模塊工廠必須返回構(gòu)造函數(shù)。
換句話說,模塊工廠必須是返回函數(shù)的函數(shù) - 高階函數(shù)(HOF)。測試用例如下
src/tests/jest_sound_player_3.test.js

import SoundPlayer from '../lib/sound-player';
import SoundPlayerConsumer from '../lib/sound-player-consumer';

jest.mock('../lib/sound-player'); // SoundPlayer 現(xiàn)在是一個模擬構(gòu)造函數(shù)

const mockPlaySoundFile = jest.fn();
const mockChoicePlaySoundFile = jest.fn();

jest.mock('../lib/sound-player', () => jest.fn().mockImplementation(() => ({
  choicePlaySoundFile: mockChoicePlaySoundFile,
  playSoundFile: mockPlaySoundFile,
})));

beforeEach(() => {
  // 清除所有實例并調(diào)用構(gòu)造函數(shù)和所有方法:
  SoundPlayer.mockClear();
  mockChoicePlaySoundFile.mockClear();
});

it('我們可以檢查SoundPlayerConsumer是否調(diào)用了類構(gòu)造函數(shù)', () => {
  const soundPlayerConsumer = new SoundPlayerConsumer();
  expect(SoundPlayer).toHaveBeenCalledTimes(1);
});

it('我們可以檢查SoundPlayerConsumer是否在類實例上調(diào)用了一個方法', () => {
  const soundPlayerConsumer = new SoundPlayerConsumer();
  const coolSoundFileName = 'song.mp3';
  soundPlayerConsumer.play();
  expect(mockChoicePlaySoundFile).toHaveBeenCalledWith(coolSoundFileName);
});

注意上面代碼中的這段代碼

const mockPlaySoundFile = jest.fn();
const mockChoicePlaySoundFile = jest.fn();

jest.mock('../lib/sound-player', () => jest.fn().mockImplementation(() => ({
  choicePlaySoundFile: mockChoicePlaySoundFile,
  playSoundFile: mockPlaySoundFile,
})));

工廠參數(shù)的限制是,由于對jest.mock()的調(diào)用被提升到文件的頂部,因此無法首先定義變量然后在工廠中使用它。
對以"mock"開頭的變量進行例外處理。

ES6語法的類測試實例四 - 使用mockImplementation()或mockImplementationOnce()替換mock(Replacing the mock using mockImplementation() or mockImplementationOnce())您可以通過在現(xiàn)有模擬上

調(diào)用mockImplementation()來替換前面所有的模擬,以便更改單個測試或所有測試的實現(xiàn)。
對jest.mock的調(diào)用被提升到代碼的頂部。
也可以指定模擬,例如在beforeAll()中,通過在現(xiàn)有mock上調(diào)用mockImplementation()或mockImplementationOnce()而不是使用factory參數(shù)。
如果需要,這還允許在測試之間更改模擬:測試用例如下

import SoundPlayer from '../lib/sound-player';
import SoundPlayerConsumer from '../lib/sound-player-consumer';

jest.mock('../lib/sound-player'); // SoundPlayer 現(xiàn)在是一個模擬構(gòu)造函數(shù)

describe('SoundPlayer被調(diào)用的時候拋出異常', () => {
  beforeAll(() => {
    SoundPlayer.mockImplementation(() => ({
      playSoundFile: () => {
        throw new Error('Test error');
      },
      choicePlaySoundFile: () => {
        throw new Error('Test error');
      },
    }));
  });

  it('play被調(diào)用的收拋出異常', () => {
    const soundPlayerConsumer = new SoundPlayerConsumer();
    expect(() => soundPlayerConsumer.play()).toThrow();
  });
});

上面的代碼注意這里

beforeAll(() => {
  SoundPlayer.mockImplementation(() => ({
    playSoundFile: () => {
      throw new Error('Test error');
    },
    choicePlaySoundFile: () => {
      throw new Error('Test error');
    },
  }));
});

實踐項目地址

git clone https://github.com/durban89/webpack4-react16-reactrouter-demo.git
git checkout v_1.0.32
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時請結(jié)合常識與多方信息審慎甄別。
平臺聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點,簡書系信息發(fā)布平臺,僅提供信息存儲服務。

相關閱讀更多精彩內(nèi)容

友情鏈接更多精彩內(nèi)容