はじめに
今まで関数のモックはpropsを通してjest.fn()
を渡すことでしかできないと思っていたが、任意の関数(hooks)の戻り値をモック化できた。
全ソースコード:GitHub
モック対象の関数
useRandom.ts
import { useState } from 'react';
// min以上max未満の乱数を使えるhooks
export function useRandom(initialValue?: number): [number, (min: number, max: number) => void] {
const [value, setValue] = useState<number>(initialValue ? initialValue : 0);
return [
value,
(min: number, max: number) => setValue(Math.floor(Math.random() * (max - min)) + min),
];
}
関数を利用するコンポーネント
App.tsx
import React from 'react';
import './App.css';
import { useRandom } from './useRandom';
const App: React.FC = () => {
const [value, setNewRandom] = useRandom();
return (
<div className='App'>
<button onClick={() => setNewRandom(0, 100)}>New</button>
<p data-testid='value'>{value === 7 ? `Lucky ${value}` : value}</p>
</div>
);
};
export default App;
テスト
App.test.tsx
import React from 'react';
import { render, cleanup } from '@testing-library/react';
import App from './App';
import { useRandom } from './useRandom';
jest.mock('./useRandom');
const useRandomMock = useRandom as jest.MockedFunction<typeof useRandom>;
afterEach(cleanup);
it('value===7のとき "Lucky 7" と表示される', () => {
useRandomMock.mockReturnValue([7, () => {}]);
const { getByTestId } = render(<App />);
const value = getByTestId('value');
expect(value.textContent).toEqual('Lucky 7');
});