寻找元素
前缀
- Get:返回查询的匹配节点,如果没元素匹配,则会报错(针对单查如果查到多个也会报错);
- Query:返回查询的匹配节点,如果没有元素匹配会返回 null,但是不会报错(同样针对单查,如果查到多个匹配元素也会报错)
- Find:返回一个 Promise,默认超时时间为 1000 ms, 如果没有元素匹配或者查找超时,Promise 状态切为 reject(同样针对单查,如果查到多个元素,也会返回 reject)。
后缀
| 前缀 | 后缀 |
|---|---|
| get query find | role(角色) |
| labelText (标签文本) | |
| placeholderText (暗纹) | |
| text (文本) | |
| displayValue (表单值) | |
| altText (图片alt) | |
| title (标题) | |
| testid (如果前面都用不了,那么改代码加testid) |
role
role 是dom元素的隐藏属性,如
<button>按钮</button>
// 相遇于
<button role="button">按钮</button>
常见的role属性对照可以查看W3C 对应的提案
| 标签 | 属性 |
|---|---|
| a , href | link |
| a (没有 href 属性), body, div, span | generic |
| form | form |
| h1 到 h6 | heading |
| html | document |
| img | img |
| p | paragraph |
| table | table |
| url | list |
| li | listitem |
另外还可以通过name属性在诸多一样的元素中寻找特定的那个
// 代码
<div aria-label="test_note">1234</div>
// 单测代码
const note = screen.getByRole("generic", { name: "test_note" });
labelText
标签文本(labelText):针对 label 标签的 text 查询,通过这个可以查询到对应 label 的输入节点(比如 input)
// 代码
<label> testLabel <input /> </label>
// 单测
const label = screen.getByLabelText("testLabel");
placeholdertext
暗纹(placeholdertext): 通过 placeholder 来查询,也可以有效查到对应的表单元素,如果你没有使用 label 标签的时候,可以使用这个来作为替代
// 代码
<Input
maxLength={100}
showCount
placeholder="请输入人员姓名"
style={{ width: rowWidth }}
disabled
/>
// 单测
const input2 = screen.getByPlaceholderText('请输入人员姓名')
text
text(文本内容),用来找又指定文字的元素
// 代码
<button>确定</button>
// 单测
const confrimBtn = await screen.findByText('确 定')
img alt
这个是根据 img 的 alt 来查询
// 代码
<img src="111" />
//单测
const altImg = screen.getByAltText("111");
title
这个是靠元素的title提示来找元素的
// 代码
<div title="111" >123</div>
//单测
const altImg = screen.getByTitle("111");
testid
如果你前面的都不能用上,那么还是给留了个作弊一样的方法,这就需要新增新增 data-testid 属性来进行查询
// 代码
<div data-testid="111">123</div>
//单测
const altImg = screen.getByTestId("111");
页面元素断言
断言使用场景断言
| 断言试用场景 | 断言api |
|---|---|
| 页面可见 | toBeEmptyDOMElement toBeVisible toBeInTheDocument toHaveTextContent |
| 表单验证 | toBeDisabled toBeEnabled toBeRequired toHaveFocus toBeChecked toHaveFormValues toHaveValue |
| 代码层面验证 | toHaveAttribute toHaveClass toHaveStyle |
Mock引用
mock一个function
jest.mock('next/config', () => ({
__esModule: true,
default: () => ({
publicRuntimeConfig: {
STATIC_ASSETS_URL: '111',
API_HOST: '111',
},
}),
}));
mock一个返回
jest.mock('ahooks', () =>
jest.fn().mockReturnValue({
data: [],
error: false,
loading: false,
refresh: false,
}),
);
mock api
import {getChannelList} from '@/api/op';
jest.mock('@/api/op');
const mockedGetChannelList = getChannelList as jest.MockedFunction<typeof getChannelList>;
describe('ChannelManagement', () => {
it('renders the table with correct columns', async () => {
const mockData = [
{
id: 100076,
name: '我是个名称',
},
];
mockedGetChannelList.mockResolvedValue({
content: mockData,
totalElements: 720,
});
render(<ChannelManagement />);
// test something
});
})
实用技巧
antd select下拉写法
<Select
placeholder="时间精度"
data-testid="select-dateType"
options={dateOptions}
defaultValue={'DAY'}
onChange={(v: string) => setDateType(v)}
/>
// 获取时间精度下拉框
const dateSelect = screen.getByTestId('select-dateType').firstElementChild;
// 触发时间精度下拉框的点击事件
fireEvent.mouseDown(dateSelect as Element);
// 获取下拉选项
expect(screen.queryByText('全部')).toBeInTheDocument();
expect(screen.queryByText('按周')).toBeInTheDocument();
expect(screen.queryByText('按月')).toBeInTheDocument();
fireEvent.click(screen.queryByText('按周') as Element);
antd rangepicker写法,datepicker同理
<RangePicker
format="YYYY-MM-DD"
open={open}
data-testid="select-rangePicker"
onOpenChange={(open) => handleCloseRanger(open)}
defaultValue={[
moment().subtract('days', 29),
moment().endOf('d'),
]}
allowClear={false}
disabledDate={disabledDate}
onChange={handleDateValueChange}
/>
// grab the input
const rangePicker = screen
.getByTestId('select-rangePicker')
.querySelectorAll('input')[0];
// mouseDown opens the calendar popup, set focus on the input
fireEvent.mouseDown(rangePicker);
// type date in input
fireEvent.change(rangePicker, { target: { value: '2020-01-15' } });
// now calendar popup is opened and 2020-01-15 cell is selected, just click on it
fireEvent.click(
document.querySelector('.ant-picker-cell-selected') as Element,
);
没有标识的input
没有label,没有placeholder的input,如果用form包裹,那么他就会打上id,可以考虑用queryselector
<Form.Item
name="allocationCount"
validateFirst
validateTrigger="onBlur"
>
<Input />
</Form.Item>
const allocationCount = document.querySelector('#allocationCount');
// 在搜索输入框中输入 'test'
fireEvent.change(allocationCount as Element, {
target: { value: '100' },
});