[英]Test a react component using test and react-testing-library
I just joined a team where we use react, redux, recompose to construct components to build UI.我刚刚加入了一个团队,在那里我们使用 react、redux、recompose 来构建组件来构建 UI。 There aren't any unit tests in the application and there isn't consistent architecture for the application.应用程序中没有任何单元测试,应用程序的架构也不一致。 I decided to take it upon myself to add unit tests using jest and react-testing-library.我决定自己使用 jest 和 react-testing-library 添加单元测试。 I succeed with few snapshot tests but I am struggling with unit testing.我通过很少的快照测试取得了成功,但我正在努力进行单元测试。 I am still learning react and pretty new to redux.我仍在学习 react 并且对 redux 还很陌生。 I would love some suggestion.我会喜欢一些建议。 I am going to share a component which renders a table with column and row.我将共享一个组件,该组件呈现带有列和行的表格。 I would love a feedback.我希望得到反馈。
import React, { useEffect, useState } from 'react';
import { compose } from 'recompose';
import { connect } from 'react-redux';
import { clearAll, fetchContacts } from '~/store/resources/contacts/actions';
import { isDevEnv } from '~/utils';
import Sidebar from './Sidebar';
import Table from './Table';
import Toolbar from './Toolbar';
const Contacts = ({ clearAll, fetchContacts, ...props }) => {
const [searchValue, setSearchValue] = useState('');
const [isSidebarOpen, setIsSidebarOpen] = useState(false);
const [canonicalFormValues, setCanonicalFormValues] = useState({ active: true });
useEffect(() => {
fetchContacts();
return () => {
clearAll();
};
}, []);
const closeSidebar = () => {
if (isDevEnv) {
console.log('hit close function');
}
setIsSidebarOpen(false);
};
return (
<div>
<Toolbar
searchValue={searchValue}
setSearchValue={setSearchValue}
setIsSidebarOpen={setIsSidebarOpen}
/>
<Table setCanonicalFormValues={setCanonicalFormValues} />
<Sidebar
isSidebarOpen={isSidebarOpen}
closeSidebar={closeSidebar}
canonicalFormValues={canonicalFormValues}
/>
{isDevEnv && (
<div>
This is coming from the contact folder
<br />
state values:
<br />
{JSON.stringify({ searchValue })}
<br />
{JSON.stringify({ isSidebarOpen })}
<br />
{JSON.stringify({ canonicalFormValues })}
</div>
)}
</div>
);
};
const mapDispatchToProps = {
clearAll,
fetchContacts,
};
export default compose(
connect(
null,
mapDispatchToProps,
),
)(Contacts);
I generally start out with a simple "should render without crashing" test.我通常从一个简单的“应该渲染而不会崩溃”测试开始。 I prefer to export and test the undecorated component, in your case Contacts
.我更喜欢导出和测试未修饰的组件,在您的情况下Contacts
。
export const Contacts = ({ clearAll, fetchContacts, ...props }) => { ...
In the test file在测试文件中
import React from 'react';
import { render } from '@testing-library/react';
import { Contacts } from '.';
// mock the other imported components, they should already be tested alone, right?
jest.mock('./Sidebar');
jest.mock('./Table');
jest.mock('./Toolbar');
describe('Contacts', () => {
it('should render without crashing', () = {
render(
<Contacts
// pass all the props necessary for a basic render
clearAll={jest.fn()}
fetchContacts={jest.fn()}
/>
);
});
});
At this point I run a code coverage report to see how much I have, then add more tests with varying prop values and/or using the react-testing-library's matchers to target buttons or elements to assert text is visible or trigger callbacks, etc, until I have the coverage I want.在这一点上,我运行代码覆盖率报告以查看我有多少,然后添加更多具有不同 prop 值的测试和/或使用 react-testing-library 的匹配器来定位按钮或元素以断言文本可见或触发回调等, 直到我得到我想要的报道。
Sometimes some of your components may rely on context provider, and in this case RTL allows you to specify wrappers.有时,您的某些组件可能依赖于上下文提供程序,在这种情况下,RTL 允许您指定包装器。 For example if your component gets decorated with react-intl
for string localization, you can provide a wrapper.例如,如果您的组件被用于字符串本地化的react-intl
装饰,您可以提供一个包装器。
export const Contacts = ({ clearAll, fetchContacts, intl }) => { ...
...
export default compose(
connect(
null,
mapDispatchToProps,
),
injectIntl,
)(Contacts);
Create a wrapper创建包装器
import { IntlProvider } from 'react-intl';
const IntlWrapper = ({ children }) => (
<IntlProvider locale="en">{children}</IntlProvider>
);
const intlMock = {
...
formatMessage: message => message,
...
};
and to test, specify the wrapper in the render options argument并进行测试,在渲染选项参数中指定包装器
render(
<Contacts
// pass all the props necessary for a basic render
clearAll={jest.fn()}
fetchContacts={jest.fn()}
intl={intlMock}
/>,
{
wrapper: IntlWrapper
}
);
react-testing-library
has a lot of documentation, but it is worth reading through. react-testing-library
有很多文档,但值得一读。 Hope this helps you get going.希望这可以帮助你开始。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.