Fixed issue/1465 partially got rid of enzyme in tests (#1489)

* got rid of enzyme in Dropdown tests

* got rid of enzyme in DynamicTextButton tests

* got rid of enzyme in Search tests

* Revert "got rid of enzyme in Search tests"

This reverts commit cd2c5b10ab.

* got rid of enzyme in Search tests

* got rid of enzyme in SQLEditor tests

* got rid of enzyme in Connect tests

* got rid of enzyme in Connect/Details tests

* got rid of enzyme in Topics\Topic tests

* got rid of ThemeProvider in render function

* fixed redundant

* used userEvent instead of fireEvent

* fixed snapshot tests

* used screen

* rise testing-library approach

* got rid of snapshot in Search component test

* changed titles of Search component test

* fixed topics details test
This commit is contained in:
Denys Malofeiev 2022-02-04 22:34:34 +02:00 committed by GitHub
parent f6daa8c69c
commit 54bd778d9c
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
15 changed files with 548 additions and 967 deletions

View file

@ -1,7 +1,10 @@
import React from 'react'; import React from 'react';
import { create } from 'react-test-renderer'; import { create } from 'react-test-renderer';
import { mount } from 'enzyme'; import {
import { containerRendersView, TestRouterWrapper } from 'lib/testHelpers'; containerRendersView,
TestRouterWrapper,
render,
} from 'lib/testHelpers';
import { clusterConnectConnectorPath } from 'lib/paths'; import { clusterConnectConnectorPath } from 'lib/paths';
import DetailsContainer from 'components/Connect/Details/DetailsContainer'; import DetailsContainer from 'components/Connect/Details/DetailsContainer';
import Details, { DetailsProps } from 'components/Connect/Details/Details'; import Details, { DetailsProps } from 'components/Connect/Details/Details';
@ -79,13 +82,13 @@ describe('Details', () => {
}); });
it('is empty when no connector', () => { it('is empty when no connector', () => {
const wrapper = mount(setupWrapper({ connector: null })); const wrapper = render(setupWrapper({ connector: null })).baseElement;
expect(wrapper.html()).toEqual(''); expect(wrapper.querySelector('div')).toBeEmptyDOMElement();
}); });
it('fetches connector on mount', () => { it('fetches connector on mount', () => {
const fetchConnector = jest.fn(); const fetchConnector = jest.fn();
mount(setupWrapper({ fetchConnector })); render(setupWrapper({ fetchConnector }));
expect(fetchConnector).toHaveBeenCalledTimes(1); expect(fetchConnector).toHaveBeenCalledTimes(1);
expect(fetchConnector).toHaveBeenCalledWith( expect(fetchConnector).toHaveBeenCalledWith(
clusterName, clusterName,
@ -96,7 +99,7 @@ describe('Details', () => {
it('fetches tasks on mount', () => { it('fetches tasks on mount', () => {
const fetchTasks = jest.fn(); const fetchTasks = jest.fn();
mount(setupWrapper({ fetchTasks })); render(setupWrapper({ fetchTasks }));
expect(fetchTasks).toHaveBeenCalledTimes(1); expect(fetchTasks).toHaveBeenCalledTimes(1);
expect(fetchTasks).toHaveBeenCalledWith( expect(fetchTasks).toHaveBeenCalledWith(
clusterName, clusterName,

View file

@ -1,10 +1,63 @@
import React from 'react'; import React from 'react';
import { shallow } from 'enzyme'; import { render } from 'lib/testHelpers';
import { screen } from '@testing-library/react';
import Connect from 'components/Connect/Connect'; import Connect from 'components/Connect/Connect';
import { store } from 'redux/store';
import { Route } from 'react-router-dom';
import {
clusterConnectorsPath,
clusterConnectorNewPath,
clusterConnectConnectorPath,
clusterConnectConnectorEditPath,
} from 'lib/paths';
jest.mock('components/Connect/New/NewContainer', () => () => (
<div>NewContainer</div>
));
jest.mock('components/Connect/List/ListContainer', () => () => (
<div>ListContainer</div>
));
jest.mock('components/Connect/Details/DetailsContainer', () => () => (
<div>DetailsContainer</div>
));
jest.mock('components/Connect/Edit/EditContainer', () => () => (
<div>EditContainer</div>
));
describe('Connect', () => { describe('Connect', () => {
it('matches snapshot', () => { const renderComponent = (pathname: string) =>
const wrapper = shallow(<Connect />); render(
expect(wrapper).toMatchSnapshot(); <Route path="/ui/clusters/:clusterName">
<Connect />
</Route>,
{ pathname, store }
);
it('renders ListContainer', () => {
renderComponent(clusterConnectorsPath('my-cluster'));
expect(screen.getByText('ListContainer')).toBeInTheDocument();
});
it('renders NewContainer', () => {
renderComponent(clusterConnectorNewPath('my-cluster'));
expect(screen.getByText('NewContainer')).toBeInTheDocument();
});
it('renders DetailsContainer', () => {
renderComponent(
clusterConnectConnectorPath('my-cluster', 'my-connect', 'my-connector')
);
expect(screen.getByText('DetailsContainer')).toBeInTheDocument();
});
it('renders EditContainer', () => {
renderComponent(
clusterConnectConnectorEditPath(
'my-cluster',
'my-connect',
'my-connector'
)
);
expect(screen.getByText('EditContainer')).toBeInTheDocument();
}); });
}); });

View file

@ -1,34 +0,0 @@
// Jest Snapshot v1, https://goo.gl/fbAQLP
exports[`Connect matches snapshot 1`] = `
<div>
<Switch>
<BreadcrumbRoute
component={
Object {
"$$typeof": Symbol(react.memo),
"WrappedComponent": [Function],
"compare": null,
"type": [Function],
}
}
exact={true}
path="/ui/clusters/:clusterName/connectors"
/>
<BreadcrumbRoute
component={[Function]}
exact={true}
path="/ui/clusters/:clusterName/connectors/create-new"
/>
<BreadcrumbRoute
component={[Function]}
exact={true}
path="/ui/clusters/:clusterName/connects/:connectName/connectors/:connectorName/edit"
/>
<BreadcrumbRoute
component={[Function]}
path="/ui/clusters/:clusterName/connects/:connectName/connectors/:connectorName"
/>
</Switch>
</div>
`;

View file

@ -1,7 +1,7 @@
import React from 'react'; import React from 'react';
import fetchMock from 'fetch-mock'; import fetchMock from 'fetch-mock';
import { Route } from 'react-router'; import { Route } from 'react-router';
import { screen, waitFor, fireEvent } from '@testing-library/react'; import { screen, waitFor } from '@testing-library/react';
import userEvent from '@testing-library/user-event'; import userEvent from '@testing-library/user-event';
import { render } from 'lib/testHelpers'; import { render } from 'lib/testHelpers';
import { clusterConsumerGroupResetOffsetsPath } from 'lib/paths'; import { clusterConsumerGroupResetOffsetsPath } from 'lib/paths';
@ -122,9 +122,10 @@ describe('ResetOffsets', () => {
} }
); );
await waitFor(() => { await waitFor(() => {
fireEvent.change(screen.getAllByLabelText('Partition #0')[1], { userEvent.click(screen.getAllByLabelText('Partition #0')[1]);
target: { value: '10' },
}); });
await waitFor(() => {
userEvent.keyboard('10');
}); });
userEvent.click(screen.getByText('Submit')); userEvent.click(screen.getByText('Submit'));
await waitFor(() => resetConsumerGroupOffsetsMockCalled()); await waitFor(() => resetConsumerGroupOffsetsMockCalled());

View file

@ -1,17 +1,11 @@
import React from 'react'; import React from 'react';
import { mount } from 'enzyme';
import { StaticRouter } from 'react-router-dom';
import { screen } from '@testing-library/react'; import { screen } from '@testing-library/react';
import userEvent from '@testing-library/user-event'; import userEvent from '@testing-library/user-event';
import ClusterContext from 'components/contexts/ClusterContext'; import ClusterContext from 'components/contexts/ClusterContext';
import Details from 'components/Topics/Topic/Details/Details'; import Details from 'components/Topics/Topic/Details/Details';
import { internalTopicPayload } from 'redux/reducers/topics/__test__/fixtures'; import { internalTopicPayload } from 'redux/reducers/topics/__test__/fixtures';
import { Provider } from 'react-redux';
import { store } from 'redux/store';
import { ThemeProvider } from 'styled-components';
import { render } from 'lib/testHelpers'; import { render } from 'lib/testHelpers';
import { clusterTopicPath } from 'lib/paths'; import { clusterTopicPath } from 'lib/paths';
import theme from 'theme/theme';
describe('Details', () => { describe('Details', () => {
const mockDelete = jest.fn(); const mockDelete = jest.fn();
@ -45,10 +39,7 @@ describe('Details', () => {
describe('when it has readonly flag', () => { describe('when it has readonly flag', () => {
it('does not render the Action button a Topic', () => { it('does not render the Action button a Topic', () => {
const component = mount( const { baseElement } = render(
<ThemeProvider theme={theme}>
<Provider store={store}>
<StaticRouter>
<ClusterContext.Provider <ClusterContext.Provider
value={{ value={{
isReadOnly: true, isReadOnly: true,
@ -68,13 +59,10 @@ describe('Details', () => {
isDeletePolicy isDeletePolicy
/> />
</ClusterContext.Provider> </ClusterContext.Provider>
</StaticRouter>
</Provider>
</ThemeProvider>
); );
expect(component.exists('button')).toBeFalsy(); expect(screen.queryByText('Produce Message')).not.toBeInTheDocument();
expect(component).toMatchSnapshot(); expect(baseElement).toMatchSnapshot();
}); });
}); });

View file

@ -87,584 +87,47 @@ exports[`Details when it has readonly flag does not render the Action button a T
gap: 26px; gap: 26px;
} }
<Component <body>
theme={ <div>
Object {
"alert": Object {
"color": Object {
"error": "#FAD1D1",
"info": "#E3E6E8",
"success": "#D6F5E0",
"warning": "#FFEECC",
},
"shadow": "rgba(0, 0, 0, 0.1)",
},
"breadcrumb": "#ABB5BA",
"button": Object {
"border": Object {
"active": "#171A1C",
"hover": "#454F54",
"normal": "#73848C",
},
"fontSize": Object {
"L": "16px",
"M": "14px",
"S": "14px",
},
"height": Object {
"L": "40px",
"M": "32px",
"S": "24px",
},
"primary": Object {
"backgroundColor": Object {
"active": "#1414B8",
"hover": "#1717CF",
"normal": "#4F4FFF",
},
"color": "#FFFFFF",
"invertedColors": Object {
"active": "#1414B8",
"hover": "#1717CF",
"normal": "#4F4FFF",
},
},
"secondary": Object {
"backgroundColor": Object {
"active": "#D5DADD",
"hover": "#E3E6E8",
"normal": "#F1F2F3",
},
"color": "#171A1C",
"invertedColors": Object {
"active": "#171A1C",
"hover": "#454F54",
"normal": "#73848C",
},
},
},
"circularAlert": Object {
"color": Object {
"error": "#E51A1A",
"info": "#E3E6E8",
"success": "#5CD685",
"warning": "#FFEECC",
},
},
"configList": Object {
"color": "#ABB5BA",
},
"connectEditWarning": "#FFEECC",
"consumerTopicContent": Object {
"backgroundColor": "#F1F2F3",
},
"dangerZone": Object {
"borderColor": "#E3E6E8",
"color": "#E51A1A",
},
"dropdown": Object {
"color": "#E51A1A",
},
"heading": Object {
"h1": Object {
"color": "#171A1C",
},
"h3": Object {
"color": "#73848C",
"fontSize": "14px",
},
},
"icons": Object {
"closeIcon": "#ABB5BA",
"liveIcon": Object {
"circleBig": "#FAD1D1",
"circleSmall": "#E51A1A",
},
"messageToggleIconClosed": "#ABB5BA",
"messageToggleIconOpened": "#171A1C",
"verticalElipsisIcon": "#73848C",
"warningIcon": "#FFDD57",
},
"input": Object {
"backgroundColor": Object {
"readOnly": "#F1F2F3",
},
"borderColor": Object {
"disabled": "#E3E6E8",
"focus": "#454F54",
"hover": "#73848C",
"normal": "#ABB5BA",
},
"color": Object {
"disabled": "#ABB5BA",
"placeholder": Object {
"normal": "#ABB5BA",
"readOnly": "#ABB5BA",
},
"readOnly": "#171A1C",
},
"error": "#E51A1A",
"icon": Object {
"color": "#454F54",
},
"label": Object {
"color": "#454F54",
},
},
"layout": Object {
"minWidth": "1200px",
"navBarHeight": "3.25rem",
"navBarWidth": "201px",
"overlay": Object {
"backgroundColor": "#73848C",
},
"stuffBorderColor": "#E3E6E8",
"stuffColor": "#F1F2F3",
},
"menu": Object {
"backgroundColor": Object {
"active": "#E3E6E8",
"hover": "#F1F2F3",
"normal": "#FFFFFF",
},
"chevronIconColor": "#73848C",
"color": Object {
"active": "#171A1C",
"hover": "#73848C",
"normal": "#73848C",
},
"statusIconColor": Object {
"offline": "#E51A1A",
"online": "#5CD685",
},
},
"metrics": Object {
"backgroundColor": "#F1F2F3",
"filters": Object {
"color": Object {
"icon": "#171A1C",
"normal": "#73848C",
},
},
"indicator": Object {
"backgroundColor": "#FFFFFF",
"lightTextColor": "#ABB5BA",
"titleColor": "#73848C",
"warningTextColor": "#E51A1A",
},
},
"modal": Object {
"backgroundColor": "#FFFFFF",
"border": Object {
"bottom": "#F1F2F3",
"top": "#F1F2F3",
},
"overlay": "rgba(10, 10, 10, 0.1)",
"shadow": "rgba(0, 0, 0, 0.1)",
},
"pageLoader": Object {
"borderBottomColor": "#FFFFFF",
"borderColor": "#4F4FFF",
},
"pagination": Object {
"backgroundColor": "#FFFFFF",
"borderColor": Object {
"active": "#454F54",
"disabled": "#C7CED1",
"hover": "#73848C",
"normal": "#ABB5BA",
},
"color": Object {
"active": "#171A1C",
"disabled": "#C7CED1",
"hover": "#171A1C",
"normal": "#171A1C",
},
"currentPage": "#E3E6E8",
},
"panelColor": "#FFFFFF",
"primaryTab": Object {
"borderColor": Object {
"active": "#4F4FFF",
"hover": "transparent",
"nav": "#E3E6E8",
"normal": "transparent",
},
"color": Object {
"active": "#171A1C",
"hover": "#171A1C",
"normal": "#73848C",
},
},
"schema": Object {
"backgroundColor": Object {
"div": "#FFFFFF",
"tr": "#F1F2F3",
},
},
"scrollbar": Object {
"thumbColor": Object {
"active": "#73848C",
"normal": "#FFFFFF",
},
"trackColor": Object {
"active": "#F1F2F3",
"normal": "#FFFFFF",
},
},
"secondaryTab": Object {
"backgroundColor": Object {
"active": "#E3E6E8",
"hover": "#F1F2F3",
"normal": "#FFFFFF",
},
"color": Object {
"active": "#171A1C",
"hover": "#171A1C",
"normal": "#73848C",
},
},
"select": Object {
"backgroundColor": Object {
"active": "#E3E6E8",
"hover": "#E3E6E8",
"normal": "#FFFFFF",
},
"borderColor": Object {
"active": "#454F54",
"disabled": "#E3E6E8",
"hover": "#73848C",
"normal": "#ABB5BA",
},
"color": Object {
"active": "#171A1C",
"disabled": "#ABB5BA",
"hover": "#171A1C",
"normal": "#171A1C",
},
"optionList": Object {
"scrollbar": Object {
"backgroundColor": "#ABB5BA",
},
},
},
"switch": Object {
"checked": "#29A352",
"circle": "#FFFFFF",
"unchecked": "#ABB5BA",
},
"table": Object {
"link": Object {
"color": Object {
"normal": "#171A1C",
},
},
"td": Object {
"color": Object {
"normal": "#171A1C",
},
},
"th": Object {
"backgroundColor": Object {
"normal": "#FFFFFF",
},
"color": Object {
"active": "#4F4FFF",
"hover": "#4F4FFF",
"normal": "#73848C",
},
"previewColor": Object {
"normal": "#4F4FFF",
},
},
"tr": Object {
"backgroundColor": Object {
"hover": "#F1F2F3",
},
},
},
"tag": Object {
"backgroundColor": Object {
"blue": "#e3f2fd",
"gray": "#F1F2F3",
"green": "#D6F5E0",
"red": "#FAD1D1",
"white": "#E3E6E8",
"yellow": "#FFEECC",
},
"color": "#171A1C",
},
"textArea": Object {
"backgroundColor": Object {
"readOnly": "#F1F2F3",
},
"borderColor": Object {
"disabled": "#E3E6E8",
"focus": "#454F54",
"hover": "#73848C",
"normal": "#ABB5BA",
},
"color": Object {
"disabled": "#ABB5BA",
"placeholder": Object {
"focus": Object {
"normal": "transparent",
"readOnly": "#ABB5BA",
},
"normal": "#ABB5BA",
},
"readOnly": "#171A1C",
},
},
"topicFormLabel": Object {
"color": "#73848C",
},
"topicMetaData": Object {
"backgroundColor": "#F1F2F3",
"color": Object {
"label": "#73848C",
"meta": "#ABB5BA",
"value": "#2F3639",
},
},
"topicsList": Object {
"backgroundColor": Object {
"active": "#E3E6E8",
"hover": "#F1F2F3",
},
"color": Object {
"active": "#171A1C",
"hover": "#73848C",
"normal": "#171A1C",
},
},
"viewer": Object {
"wrapper": "#f9fafa",
},
}
}
>
<Provider
store={
Object {
"@@observable": [Function],
"dispatch": [Function],
"getState": [Function],
"replaceReducer": [Function],
"subscribe": [Function],
}
}
>
<StaticRouter>
<Router
history={
Object {
"action": "POP",
"block": [Function],
"createHref": [Function],
"go": [Function],
"goBack": [Function],
"goForward": [Function],
"listen": [Function],
"location": Object {
"hash": "",
"pathname": "/",
"search": "",
"state": undefined,
},
"push": [Function],
"replace": [Function],
}
}
staticContext={Object {}}
>
<Details
clearTopicMessages={[MockFunction]}
clusterName="local"
deleteTopic={[MockFunction]}
isDeletePolicy={true}
isDeleted={false}
isInternal={true}
name="__internal.topic"
topicName="__internal.topic"
>
<div> <div>
<Styled(PageHeading)
text="__internal.topic"
>
<PageHeading
className="c0"
text="__internal.topic"
>
<div <div
className="c0" class="c0"
> >
<h1> <h1>
__internal.topic __internal.topic
</h1> </h1>
<div> <div>
<styled.div>
<div <div
className="c1" class="c1"
>
<Route
exact={true}
path="/ui/clusters/:clusterName/topics/:topicName/messages"
/> />
</div> </div>
</styled.div>
</div> </div>
</div>
</PageHeading>
</Styled(PageHeading)>
<ConfirmationModal
isOpen={false}
onCancel={[Function]}
onConfirm={[Function]}
/>
<ConfirmationModal
isOpen={false}
onCancel={[Function]}
onConfirm={[Function]}
/>
<styled.nav
role="navigation"
>
<nav <nav
className="c2" class="c2"
role="navigation" role="navigation"
>
<NavLink
activeClassName="is-active is-primary"
exact={true}
to="/ui/clusters/local/topics/__internal.topic"
>
<Link
aria-current={null}
to={
Object {
"hash": "",
"pathname": "/ui/clusters/local/topics/__internal.topic",
"search": "",
"state": null,
}
}
>
<LinkAnchor
aria-current={null}
href="/ui/clusters/local/topics/__internal.topic"
navigate={[Function]}
> >
<a <a
aria-current={null}
href="/ui/clusters/local/topics/__internal.topic" href="/ui/clusters/local/topics/__internal.topic"
onClick={[Function]}
> >
Overview Overview
</a> </a>
</LinkAnchor>
</Link>
</NavLink>
<NavLink
activeClassName="is-active"
exact={true}
to="/ui/clusters/local/topics/__internal.topic/messages"
>
<Link
aria-current={null}
to={
Object {
"hash": "",
"pathname": "/ui/clusters/local/topics/__internal.topic/messages",
"search": "",
"state": null,
}
}
>
<LinkAnchor
aria-current={null}
href="/ui/clusters/local/topics/__internal.topic/messages"
navigate={[Function]}
>
<a <a
aria-current={null}
href="/ui/clusters/local/topics/__internal.topic/messages" href="/ui/clusters/local/topics/__internal.topic/messages"
onClick={[Function]}
> >
Messages Messages
</a> </a>
</LinkAnchor>
</Link>
</NavLink>
<NavLink
activeClassName="is-active"
exact={true}
to="/ui/clusters/local/topics/__internal.topic/consumer-groups"
>
<Link
aria-current={null}
to={
Object {
"hash": "",
"pathname": "/ui/clusters/local/topics/__internal.topic/consumer-groups",
"search": "",
"state": null,
}
}
>
<LinkAnchor
aria-current={null}
href="/ui/clusters/local/topics/__internal.topic/consumer-groups"
navigate={[Function]}
>
<a <a
aria-current={null}
href="/ui/clusters/local/topics/__internal.topic/consumer-groups" href="/ui/clusters/local/topics/__internal.topic/consumer-groups"
onClick={[Function]}
> >
Consumers Consumers
</a> </a>
</LinkAnchor>
</Link>
</NavLink>
<NavLink
activeClassName="is-active"
exact={true}
to="/ui/clusters/local/topics/__internal.topic/settings"
>
<Link
aria-current={null}
to={
Object {
"hash": "",
"pathname": "/ui/clusters/local/topics/__internal.topic/settings",
"search": "",
"state": null,
}
}
>
<LinkAnchor
aria-current={null}
href="/ui/clusters/local/topics/__internal.topic/settings"
navigate={[Function]}
>
<a <a
aria-current={null}
href="/ui/clusters/local/topics/__internal.topic/settings" href="/ui/clusters/local/topics/__internal.topic/settings"
onClick={[Function]}
> >
Settings Settings
</a> </a>
</LinkAnchor>
</Link>
</NavLink>
</nav> </nav>
</styled.nav>
<Switch />
</div> </div>
</Details> </div>
</Router> </body>
</StaticRouter>
</Provider>
</Component>
`; `;

View file

@ -1,8 +1,10 @@
import React from 'react'; import React from 'react';
import { mount } from 'enzyme';
import Dropdown, { DropdownProps } from 'components/common/Dropdown/Dropdown'; import Dropdown, { DropdownProps } from 'components/common/Dropdown/Dropdown';
import DropdownItem from 'components/common/Dropdown/DropdownItem'; import DropdownItem from 'components/common/Dropdown/DropdownItem';
import DropdownDivider from 'components/common/Dropdown/DropdownDivider'; import DropdownDivider from 'components/common/Dropdown/DropdownDivider';
import userEvent from '@testing-library/user-event';
import { render } from 'lib/testHelpers';
import { screen } from '@testing-library/react';
const dummyLable = 'My Test Label'; const dummyLable = 'My Test Label';
const dummyChildren = ( const dummyChildren = (
@ -25,45 +27,47 @@ describe('Dropdown', () => {
); );
it('renders Dropdown with initial props', () => { it('renders Dropdown with initial props', () => {
const wrapper = mount(setupWrapper()); const wrapper = render(setupWrapper()).baseElement;
expect(wrapper.exists('.dropdown')).toBeTruthy(); expect(wrapper.querySelector('.dropdown')).toBeTruthy();
expect(wrapper.exists('.dropdown.is-active')).toBeFalsy(); expect(wrapper.querySelector('.dropdown.is-active')).toBeFalsy();
expect(wrapper.exists('.dropdown.is-right')).toBeFalsy(); expect(wrapper.querySelector('.dropdown.is-right')).toBeFalsy();
expect(wrapper.exists('.dropdown.is-up')).toBeFalsy(); expect(wrapper.querySelector('.dropdown.is-up')).toBeFalsy();
expect(wrapper.exists('.dropdown-content')).toBeTruthy(); expect(wrapper.querySelector('.dropdown-content')).toBeTruthy();
expect(wrapper.find('.dropdown-content').text()).toEqual(''); expect(wrapper.querySelector('.dropdown-content')).toHaveTextContent('');
}); });
it('renders custom children', () => { it('renders custom children', () => {
const wrapper = mount(setupWrapper({}, dummyChildren)); const wrapper = render(setupWrapper({}, dummyChildren)).baseElement;
expect(wrapper.exists('.dropdown-content')).toBeTruthy(); expect(wrapper.querySelector('.dropdown-content')).toBeTruthy();
expect(wrapper.find('a.dropdown-item').length).toEqual(3); expect(wrapper.querySelectorAll('.dropdown-item').length).toEqual(3);
expect(wrapper.find('.dropdown-divider').length).toEqual(1); expect(wrapper.querySelectorAll('.dropdown-divider').length).toEqual(1);
}); });
it('renders dropdown with a right-aligned menu', () => { it('renders dropdown with a right-aligned menu', () => {
const wrapper = mount(setupWrapper({ right: true })); const wrapper = render(setupWrapper({ right: true })).baseElement;
expect(wrapper.exists('.dropdown.is-right')).toBeTruthy(); expect(wrapper.querySelector('.dropdown.is-right')).toBeTruthy();
}); });
it('renders dropdown with a popup menu', () => { it('renders dropdown with a popup menu', () => {
const wrapper = mount(setupWrapper({ up: true })); const wrapper = render(setupWrapper({ up: true })).baseElement;
expect(wrapper.exists('.dropdown.is-up')).toBeTruthy(); expect(wrapper.querySelector('.dropdown.is-up')).toBeTruthy();
}); });
it('handles click', () => { it('handles click', () => {
const wrapper = mount(setupWrapper()); const wrapper = render(setupWrapper()).baseElement;
expect(wrapper.exists('button')).toBeTruthy(); const button = screen.getByText('My Test Label');
expect(wrapper.exists('.dropdown.is-active')).toBeFalsy();
wrapper.find('button').simulate('click'); expect(button).toBeInTheDocument();
expect(wrapper.exists('.dropdown.is-active')).toBeTruthy(); expect(wrapper.querySelector('.dropdown.is-active')).toBeFalsy();
userEvent.click(button);
expect(wrapper.querySelector('.dropdown.is-active')).toBeTruthy();
}); });
it('matches snapshot', () => { it('matches snapshot', () => {
const wrapper = mount( const { baseElement } = render(
setupWrapper( setupWrapper(
{ {
right: true, right: true,
@ -72,6 +76,6 @@ describe('Dropdown', () => {
dummyChildren dummyChildren
) )
); );
expect(wrapper).toMatchSnapshot(); expect(baseElement).toMatchSnapshot();
}); });
}); });

View file

@ -1,23 +1,26 @@
import React from 'react'; import React from 'react';
import { mount } from 'enzyme';
import DropdownItem from 'components/common/Dropdown/DropdownItem'; import DropdownItem from 'components/common/Dropdown/DropdownItem';
import { render } from 'lib/testHelpers';
import userEvent from '@testing-library/user-event';
import { screen } from '@testing-library/react';
const onClick = jest.fn(); const onClick = jest.fn();
describe('DropdownItem', () => { describe('DropdownItem', () => {
it('matches snapshot', () => { it('matches snapshot', () => {
const wrapper = mount( const { baseElement } = render(
<DropdownItem onClick={jest.fn()}>Item 1</DropdownItem> <DropdownItem onClick={jest.fn()}>Item 1</DropdownItem>
); );
expect(onClick).not.toHaveBeenCalled(); expect(onClick).not.toHaveBeenCalled();
expect(wrapper).toMatchSnapshot(); expect(baseElement).toMatchSnapshot();
}); });
it('handles Click', () => { it('handles Click', () => {
const wrapper = mount( render(<DropdownItem onClick={onClick}>Item 1</DropdownItem>);
<DropdownItem onClick={onClick}>Item 1</DropdownItem>
); const dropDown = screen.getByText('Item 1');
wrapper.simulate('click');
userEvent.click(dropDown);
expect(onClick).toHaveBeenCalled(); expect(onClick).toHaveBeenCalled();
}); });
}); });

View file

@ -36,103 +36,59 @@ exports[`Dropdown matches snapshot 1`] = `
color: initial; color: initial;
} }
<Dropdown <body>
label="My Test Label" <div>
right={true}
up={true}
>
<div <div
className="dropdown is-right is-up" class="dropdown is-right is-up"
> >
<styled.div>
<div <div
className="c0" class="c0"
>
<styled.button
onClick={[Function]}
> >
<button <button
className="c1" class="c1"
onClick={[Function]}
type="button" type="button"
> >
My Test Label My Test Label
</button> </button>
</styled.button>
</div> </div>
</styled.div>
<div <div
className="dropdown-menu" class="dropdown-menu"
id="dropdown-menu" id="dropdown-menu"
role="menu" role="menu"
> >
<div <div
className="dropdown-content has-text-left" class="dropdown-content has-text-left"
>
<DropdownItem
onClick={[MockFunction]}
>
<styled.a
$isDanger={false}
className="dropdown-item is-link"
onClick={[Function]}
> >
<a <a
className="c2 dropdown-item is-link" class="c2 dropdown-item is-link"
href="#end" href="#end"
onClick={[Function]}
role="menuitem" role="menuitem"
type="button" type="button"
> >
Child 1 Child 1
</a> </a>
</styled.a>
</DropdownItem>
<DropdownItem
onClick={[MockFunction]}
>
<styled.a
$isDanger={false}
className="dropdown-item is-link"
onClick={[Function]}
>
<a <a
className="c2 dropdown-item is-link" class="c2 dropdown-item is-link"
href="#end" href="#end"
onClick={[Function]}
role="menuitem" role="menuitem"
type="button" type="button"
> >
Child 2 Child 2
</a> </a>
</styled.a>
</DropdownItem>
<DropdownDivider>
<hr <hr
className="dropdown-divider" class="dropdown-divider"
/> />
</DropdownDivider>
<DropdownItem
onClick={[MockFunction]}
>
<styled.a
$isDanger={false}
className="dropdown-item is-link"
onClick={[Function]}
>
<a <a
className="c2 dropdown-item is-link" class="c2 dropdown-item is-link"
href="#end" href="#end"
onClick={[Function]}
role="menuitem" role="menuitem"
type="button" type="button"
> >
Child 3 Child 3
</a> </a>
</styled.a>
</DropdownItem>
</div> </div>
</div> </div>
</div> </div>
</Dropdown> </div>
</body>
`; `;

View file

@ -5,23 +5,16 @@ exports[`DropdownItem matches snapshot 1`] = `
color: initial; color: initial;
} }
<DropdownItem <body>
onClick={[MockFunction]} <div>
>
<styled.a
$isDanger={false}
className="dropdown-item is-link"
onClick={[Function]}
>
<a <a
className="c0 dropdown-item is-link" class="c0 dropdown-item is-link"
href="#end" href="#end"
onClick={[Function]}
role="menuitem" role="menuitem"
type="button" type="button"
> >
Item 1 Item 1
</a> </a>
</styled.a> </div>
</DropdownItem> </body>
`; `;

View file

@ -1,31 +1,36 @@
import React from 'react'; import React from 'react';
import { mount, shallow } from 'enzyme';
import DynamicTextButton from 'components/common/DynamicTextButton/DynamicTextButton'; import DynamicTextButton from 'components/common/DynamicTextButton/DynamicTextButton';
import { render } from 'lib/testHelpers';
import userEvent from '@testing-library/user-event';
import { screen } from '@testing-library/react';
describe('DynamicButton', () => { describe('DynamicButton', () => {
const mockCallback = jest.fn(); const mockCallback = jest.fn();
it('exectutes callback', () => { it('exectutes callback', () => {
const component = shallow( render(
<DynamicTextButton <DynamicTextButton
onClick={mockCallback} onClick={mockCallback}
title="title" title="title"
render={() => 'text'} render={() => 'text'}
/> />
); );
component.simulate('click');
userEvent.click(screen.getByTitle('title'));
expect(mockCallback).toBeCalled(); expect(mockCallback).toBeCalled();
}); });
it('changes the text', () => { it('changes the text', () => {
const component = mount( render(
<DynamicTextButton <DynamicTextButton
onClick={mockCallback} onClick={mockCallback}
title="title" title="title"
render={(clicked) => (clicked ? 'active' : 'default')} render={(clicked) => (clicked ? 'active' : 'default')}
/> />
); );
expect(component.text()).toEqual('default');
component.simulate('click'); const button = screen.getByTitle('title');
expect(component.text()).toEqual('active'); expect(button).toHaveTextContent('default');
userEvent.click(button);
expect(button).toHaveTextContent('active');
}); });
}); });

View file

@ -1,20 +1,22 @@
import { shallow } from 'enzyme';
import React from 'react'; import React from 'react';
import SQLEditor from 'components/common/SQLEditor/SQLEditor'; import SQLEditor from 'components/common/SQLEditor/SQLEditor';
import { render } from 'lib/testHelpers';
describe('SQLEditor component', () => { describe('SQLEditor component', () => {
it('matches the snapshot', () => { it('matches the snapshot', () => {
const component = shallow(<SQLEditor value="" name="name" />); const { baseElement } = render(<SQLEditor value="" name="name" />);
expect(component).toMatchSnapshot(); expect(baseElement).toMatchSnapshot();
}); });
it('matches the snapshot with fixed height', () => { it('matches the snapshot with fixed height', () => {
const component = shallow(<SQLEditor value="" name="name" isFixedHeight />); const { baseElement } = render(
expect(component).toMatchSnapshot(); <SQLEditor value="" name="name" isFixedHeight />
);
expect(baseElement).toMatchSnapshot();
}); });
it('matches the snapshot with fixed height with no value', () => { it('matches the snapshot with fixed height with no value', () => {
const component = shallow(<SQLEditor name="name" isFixedHeight />); const { baseElement } = render(<SQLEditor name="name" isFixedHeight />);
expect(component).toMatchSnapshot(); expect(baseElement).toMatchSnapshot();
}); });
}); });

View file

@ -1,126 +1,295 @@
// Jest Snapshot v1, https://goo.gl/fbAQLP // Jest Snapshot v1, https://goo.gl/fbAQLP
exports[`SQLEditor component matches the snapshot 1`] = ` exports[`SQLEditor component matches the snapshot 1`] = `
<ReactAce <body>
cursorStart={1} <div>
editorProps={Object {}} <div
enableBasicAutocompletion={false} class=" ace_editor ace_hidpi ace-tm"
enableLiveAutocompletion={false} id="name"
enableSnippets={false} style="width: 100%; height: 372px; font-size: 12px;"
focus={false} >
fontSize={12} <textarea
height="372px" autocapitalize="off"
highlightActiveLine={true} autocorrect="off"
maxLines={null} class="ace_text-input"
minLines={null} spellcheck="false"
mode="sql" style="opacity: 0; font-size: 1px;"
name="name" wrap="off"
navigateToFileEnd={true} />
onChange={null} <div
onLoad={null} aria-hidden="true"
onPaste={null} class="ace_gutter"
onScroll={null} >
placeholder={null} <div
readOnly={false} class="ace_layer ace_gutter-layer ace_folding-enabled"
scrollMargin={ style="height: 1000000px;"
Array [ />
0, </div>
0, <div
0, class="ace_scroller"
0, style="line-height: 0px;"
] >
} <div
setOptions={Object {}} class="ace_content"
showGutter={true} >
showPrintMargin={true} <div
style={Object {}} class="ace_layer ace_print-margin-layer"
tabSize={2} >
theme="textmate" <div
value="" class="ace_print-margin"
width="100%" style="left: 4px; visibility: visible;"
wrapEnabled={true} />
/> </div>
<div
class="ace_layer ace_marker-layer"
/>
<div
class="ace_layer ace_text-layer"
style="height: 1000000px; margin: 0px 4px;"
/>
<div
class="ace_layer ace_marker-layer"
/>
<div
class="ace_layer ace_cursor-layer ace_hidden-cursors"
>
<div
class="ace_cursor"
/>
</div>
</div>
</div>
<div
class="ace_scrollbar ace_scrollbar-v"
style="display: none; width: 20px;"
>
<div
class="ace_scrollbar-inner"
style="width: 20px;"
>
 
</div>
</div>
<div
class="ace_scrollbar ace_scrollbar-h"
style="display: none; height: 20px;"
>
<div
class="ace_scrollbar-inner"
style="height: 20px;"
>
 
</div>
</div>
<div
style="height: auto; width: auto; top: 0px; left: 0px; visibility: hidden; position: absolute; white-space: pre; overflow: hidden;"
>
<div
style="height: auto; width: auto; top: 0px; left: 0px; visibility: hidden; position: absolute; white-space: pre; overflow: visible;"
/>
<div
style="height: auto; width: auto; top: 0px; left: 0px; visibility: hidden; position: absolute; white-space: pre; overflow: visible;"
>
XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX
</div>
</div>
</div>
</div>
</body>
`; `;
exports[`SQLEditor component matches the snapshot with fixed height 1`] = ` exports[`SQLEditor component matches the snapshot with fixed height 1`] = `
<ReactAce <body>
cursorStart={1} <div>
editorProps={Object {}} <div
enableBasicAutocompletion={false} class=" ace_editor ace_hidpi ace-tm"
enableLiveAutocompletion={false} id="name"
enableSnippets={false} style="width: 100%; height: 16px; font-size: 12px;"
focus={false} >
fontSize={12} <textarea
height="16px" autocapitalize="off"
highlightActiveLine={true} autocorrect="off"
maxLines={null} class="ace_text-input"
minLines={null} spellcheck="false"
mode="sql" style="opacity: 0; font-size: 1px;"
name="name" wrap="off"
navigateToFileEnd={true} />
onChange={null} <div
onLoad={null} aria-hidden="true"
onPaste={null} class="ace_gutter"
onScroll={null} >
placeholder={null} <div
readOnly={false} class="ace_layer ace_gutter-layer ace_folding-enabled"
scrollMargin={ style="height: 1000000px;"
Array [ />
0, </div>
0, <div
0, class="ace_scroller"
0, style="line-height: 0px;"
] >
} <div
setOptions={Object {}} class="ace_content"
showGutter={true} >
showPrintMargin={true} <div
style={Object {}} class="ace_layer ace_print-margin-layer"
tabSize={2} >
theme="textmate" <div
value="" class="ace_print-margin"
width="100%" style="left: 4px; visibility: visible;"
wrapEnabled={true} />
/> </div>
<div
class="ace_layer ace_marker-layer"
/>
<div
class="ace_layer ace_text-layer"
style="height: 1000000px; margin: 0px 4px;"
/>
<div
class="ace_layer ace_marker-layer"
/>
<div
class="ace_layer ace_cursor-layer ace_hidden-cursors"
>
<div
class="ace_cursor"
/>
</div>
</div>
</div>
<div
class="ace_scrollbar ace_scrollbar-v"
style="display: none; width: 20px;"
>
<div
class="ace_scrollbar-inner"
style="width: 20px;"
>
 
</div>
</div>
<div
class="ace_scrollbar ace_scrollbar-h"
style="display: none; height: 20px;"
>
<div
class="ace_scrollbar-inner"
style="height: 20px;"
>
 
</div>
</div>
<div
style="height: auto; width: auto; top: 0px; left: 0px; visibility: hidden; position: absolute; white-space: pre; overflow: hidden;"
>
<div
style="height: auto; width: auto; top: 0px; left: 0px; visibility: hidden; position: absolute; white-space: pre; overflow: visible;"
/>
<div
style="height: auto; width: auto; top: 0px; left: 0px; visibility: hidden; position: absolute; white-space: pre; overflow: visible;"
>
XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX
</div>
</div>
</div>
</div>
</body>
`; `;
exports[`SQLEditor component matches the snapshot with fixed height with no value 1`] = ` exports[`SQLEditor component matches the snapshot with fixed height with no value 1`] = `
<ReactAce <body>
cursorStart={1} <div>
editorProps={Object {}} <div
enableBasicAutocompletion={false} class=" ace_editor ace_hidpi ace-tm"
enableLiveAutocompletion={false} id="name"
enableSnippets={false} style="width: 100%; height: 512px; font-size: 12px;"
focus={false} >
fontSize={12} <textarea
height="512px" autocapitalize="off"
highlightActiveLine={true} autocorrect="off"
maxLines={null} class="ace_text-input"
minLines={null} spellcheck="false"
mode="sql" style="opacity: 0; font-size: 1px;"
name="name" wrap="off"
navigateToFileEnd={true} />
onChange={null} <div
onLoad={null} aria-hidden="true"
onPaste={null} class="ace_gutter"
onScroll={null} >
placeholder={null} <div
readOnly={false} class="ace_layer ace_gutter-layer ace_folding-enabled"
scrollMargin={ style="height: 1000000px;"
Array [ />
0, </div>
0, <div
0, class="ace_scroller"
0, style="line-height: 0px;"
] >
} <div
setOptions={Object {}} class="ace_content"
showGutter={true} >
showPrintMargin={true} <div
style={Object {}} class="ace_layer ace_print-margin-layer"
tabSize={2} >
theme="textmate" <div
width="100%" class="ace_print-margin"
wrapEnabled={true} style="left: 4px; visibility: visible;"
/> />
</div>
<div
class="ace_layer ace_marker-layer"
/>
<div
class="ace_layer ace_text-layer"
style="height: 1000000px; margin: 0px 4px;"
/>
<div
class="ace_layer ace_marker-layer"
/>
<div
class="ace_layer ace_cursor-layer ace_hidden-cursors"
>
<div
class="ace_cursor"
/>
</div>
</div>
</div>
<div
class="ace_scrollbar ace_scrollbar-v"
style="display: none; width: 20px;"
>
<div
class="ace_scrollbar-inner"
style="width: 20px;"
>
 
</div>
</div>
<div
class="ace_scrollbar ace_scrollbar-h"
style="display: none; height: 20px;"
>
<div
class="ace_scrollbar-inner"
style="height: 20px;"
>
 
</div>
</div>
<div
style="height: auto; width: auto; top: 0px; left: 0px; visibility: hidden; position: absolute; white-space: pre; overflow: hidden;"
>
<div
style="height: auto; width: auto; top: 0px; left: 0px; visibility: hidden; position: absolute; white-space: pre; overflow: visible;"
/>
<div
style="height: auto; width: auto; top: 0px; left: 0px; visibility: hidden; position: absolute; white-space: pre; overflow: visible;"
>
XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX
</div>
</div>
</div>
</div>
</body>
`; `;

View file

@ -1,8 +1,8 @@
import { shallow, mount } from 'enzyme';
import Search from 'components/common/Search/Search'; import Search from 'components/common/Search/Search';
import React from 'react'; import React from 'react';
import { ThemeProvider } from 'styled-components'; import { render } from 'lib/testHelpers';
import theme from 'theme/theme'; import userEvent from '@testing-library/user-event';
import { screen } from '@testing-library/react';
jest.mock('use-debounce', () => ({ jest.mock('use-debounce', () => ({
useDebouncedCallback: (fn: (e: Event) => void) => fn, useDebouncedCallback: (fn: (e: Event) => void) => fn,
@ -11,36 +11,34 @@ jest.mock('use-debounce', () => ({
describe('Search', () => { describe('Search', () => {
const handleSearch = jest.fn(); const handleSearch = jest.fn();
it('calls handleSearch on input', () => { it('calls handleSearch on input', () => {
const component = mount( render(
<ThemeProvider theme={theme}>
<Search
handleSearch={handleSearch}
value=""
placeholder="Search bt the Topic name"
/>
</ThemeProvider>
);
component.find('input').simulate('change', { target: { value: 'test' } });
expect(handleSearch).toHaveBeenCalledTimes(1);
});
describe('when placeholder is provided', () => {
const component = shallow(
<Search <Search
handleSearch={handleSearch} handleSearch={handleSearch}
value="" value=""
placeholder="Search bt the Topic name" placeholder="Search bt the Topic name"
/> />
); );
it('matches the snapshot', () => { const input = screen.getByPlaceholderText('Search bt the Topic name');
expect(component).toMatchSnapshot(); userEvent.click(input);
}); userEvent.keyboard('value');
expect(handleSearch).toHaveBeenCalledTimes(5);
}); });
describe('when placeholder is not provided', () => { it('when placeholder is provided', () => {
const component = shallow(<Search handleSearch={handleSearch} value="" />); render(
it('matches the snapshot', () => { <Search
expect(component).toMatchSnapshot(); handleSearch={handleSearch}
value=""
placeholder="Search bt the Topic name"
/>
);
expect(
screen.getByPlaceholderText('Search bt the Topic name')
).toBeInTheDocument();
}); });
it('when placeholder is not provided', () => {
render(<Search handleSearch={handleSearch} value="" />);
expect(screen.queryByPlaceholderText('Search')).toBeInTheDocument();
}); });
}); });

View file

@ -1,23 +0,0 @@
// Jest Snapshot v1, https://goo.gl/fbAQLP
exports[`Search when placeholder is not provided matches the snapshot 1`] = `
<Styled(Input)
defaultValue=""
inputSize="M"
leftIcon="fas fa-search"
onChange={[Function]}
placeholder="Search"
type="text"
/>
`;
exports[`Search when placeholder is provided matches the snapshot 1`] = `
<Styled(Input)
defaultValue=""
inputSize="M"
leftIcon="fas fa-search"
onChange={[Function]}
placeholder="Search bt the Topic name"
type="text"
/>
`;