我们使用jest框架+ts-jest预处理+React Testing Library库。这里只说明一下本项目的button是如何测试的,别的组件当然会有不一样的地方,所以其它知识麻烦同学们自己去了解一下。
- 组件正确渲染了没有?
- 回调函数能否正确触发?
- 各种接口是否有效?
结构参考antd的,把每个组件视作一个单元,每个单元下的__tests__
文件夹应包含
index.test.tsx
- snapshots 这个文件夹是快照,是生成的不需要编写。
describe()
是jest的函数,声明一个模块,接收第一个参数是这模块的名字,第二个是回调函数,里面一般是许多个it或test函数。it()
和test()
是真正测试功能的,第一个参数是要测试的功能的描述,第二个参数是回调函数。
it('Button should render correctly', () => {
const { getByTestId } = render(
<div data-testid="button">
<Button>default</Button>
<Button type="primary">primary</Button>
<Button type="info">info</Button>
<Button type="warning">warning</Button>
<Button type="danger">danger</Button>
<Button type="dashed">dashed</Button>
<Button type="text">text</Button>
</div>,
);
expect(getByTestId('button')).toMatchSnapshot();
});
首先用RTL库的render函数和getByTestId方法获取元素,然后和快照比对一下(如果没有生成过快照,就会生成)。注意,可以用npm test -- -u
覆写快照。
button比较简单,就只有onClick函数。
it('should call onClick when clicked', () => {
const onClick = jest.fn();
const { getByTestId } = render(
<Button data-testid="button" onClick={onClick} />,
);
const btn = getByTestId('button');
fireEvent.click(btn);
expect(onClick).toBeCalled();
expect(onClick).toBeCalledTimes(1);
});
jest.fn()可以模拟一个函数,然后fireEvent可以模拟操作。
it('should render a link tag when type equals link and href is provided', () => {
const { getByTestId } = render(
<Button data-testid="button" type="link" href="https://www.baidu.com">
Link
</Button>,
);
const element = getByTestId('button');
expect(element.tagName).toEqual('A');
expect(element.classList.contains('l-btn')).toBe(true);
expect(element.classList.contains('l-btn-link')).toBe(true);
});
通过getByTestId返回的直接就是HTMLElement类型的节点。
同第一个测试,生成快照
it('should render disabled button correctly', () => {
const fn = jest.fn();
const { getByTestId } = render(
<Button disabled onClick={fn} data-testid="button_disabled">
disabled
</Button>,
);
const element = getByTestId('button_disabled');
expect(element).toHaveAttribute('disabled');
fireEvent.click(element);
expect(fn).not.toHaveBeenCalled();
});
通过fireEvent模拟点击事件
it('should not render as link button when href is undefined', async () => {
const { container } = render(
<Button type="link" href={undefined} data-testid="button_link_nohref">
button
</Button>,
);
expect(container.querySelector('a')).toBeNull();
expect(container.querySelector('a')).not.toBeNull();
});
link会渲染成a标签,只需要测试一下能不能找到a标签
在src/tests下编写公用的hook,目前有一个参考antd的mount函数,测试更新和卸载时组件是否正确。