Skip to content

Commit

Permalink
Test(widgets-list): add tests (#3697)
Browse files Browse the repository at this point in the history
  • Loading branch information
erezrokah committed May 4, 2020
1 parent 628eee4 commit 0504c58
Show file tree
Hide file tree
Showing 5 changed files with 793 additions and 1 deletion.
1 change: 1 addition & 0 deletions jest.config.js
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@ module.exports = {
'netlify-cms-ui-default': '<rootDir>/packages/netlify-cms-ui-default/src/index.js',
'netlify-cms-backend-github': '<rootDir>/packages/netlify-cms-backend-github/src/index.ts',
'netlify-cms-lib-widgets': '<rootDir>/packages/netlify-cms-lib-widgets/src/index.ts',
'netlify-cms-widget-object': '<rootDir>/packages/netlify-cms-widget-object/src/index.js',
},
testURL: 'http://localhost:8080',
};
2 changes: 1 addition & 1 deletion packages/netlify-cms-ui-default/src/ObjectWidgetTopBar.js
Original file line number Diff line number Diff line change
Expand Up @@ -109,7 +109,7 @@ class ObjectWidgetTopBar extends React.Component {
return (
<TopBarContainer>
<ExpandButtonContainer hasHeading={!!heading}>
<ExpandButton onClick={onCollapseToggle}>
<ExpandButton onClick={onCollapseToggle} data-testid="expand-button">
<Icon type="chevron" direction={collapsed ? 'right' : 'down'} size="small" />
</ExpandButton>
{heading}
Expand Down
2 changes: 2 additions & 0 deletions packages/netlify-cms-widget-list/src/ListControl.js
Original file line number Diff line number Diff line change
Expand Up @@ -388,6 +388,7 @@ export default class ListControl extends React.Component {
onCollapseToggle={partial(this.handleItemCollapseToggle, index)}
onRemove={partial(this.handleRemove, index, key)}
dragHandleHOC={SortableHandle}
data-testid={`styled-list-item-top-bar-${key}`}
/>
<NestedObjectLabel collapsed={collapsed}>{this.objectLabel(item)}</NestedObjectLabel>
<ClassNames>
Expand All @@ -412,6 +413,7 @@ export default class ListControl extends React.Component {
controlRef={controlRef}
validationKey={key}
collapsed={collapsed}
data-testid={`object-control-${key}`}
/>
)}
</ClassNames>
Expand Down
273 changes: 273 additions & 0 deletions packages/netlify-cms-widget-list/src/__tests__/ListControl.spec.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,273 @@
import React from 'react';
import { render, fireEvent } from '@testing-library/react';
import { fromJS } from 'immutable';
import ListControl from '../ListControl';

jest.mock('netlify-cms-widget-object', () => {
const React = require('react');

class MockObjectControl extends React.Component {
render() {
return <mock-object-control {...this.props}>{this.props.children}</mock-object-control>;
}
}

return {
controlComponent: MockObjectControl,
};
});
jest.mock('netlify-cms-ui-default', () => {
const actual = jest.requireActual('netlify-cms-ui-default');
const ListItemTopBar = props => (
<mock-list-item-top-bar {...props} onClick={props.onCollapseToggle}>
{props.children}
</mock-list-item-top-bar>
);
return {
...actual,
ListItemTopBar,
};
});
jest.mock('uuid/v4');

describe('ListControl', () => {
const props = {
onChange: jest.fn(),
onChangeObject: jest.fn(),
onValidateObject: jest.fn(),
validate: jest.fn(),
mediaPaths: fromJS({}),
getAsset: jest.fn(),
onOpenMediaLibrary: jest.fn(),
onAddAsset: jest.fn(),
onRemoveInsertedMedia: jest.fn(),
classNameWrapper: 'classNameWrapper',
setActiveStyle: jest.fn(),
setInactiveStyle: jest.fn(),
editorControl: jest.fn(),
resolveWidget: jest.fn(),
clearFieldErrors: jest.fn(),
fieldsErrors: fromJS({}),
};

beforeEach(() => {
jest.clearAllMocks();
const uuid = require('uuid/v4');
let id = 0;
uuid.mockImplementation(() => {
return id++;
});
});
it('should render empty list', () => {
const field = fromJS({ name: 'list', label: 'List' });
const { asFragment } = render(<ListControl {...props} field={field} />);

expect(asFragment()).toMatchSnapshot();
});

it('should render list with string array', () => {
const field = fromJS({ name: 'list', label: 'List' });
const { asFragment } = render(
<ListControl {...props} field={field} value={fromJS(['item 1', 'item 2'])} />,
);

expect(asFragment()).toMatchSnapshot();
});

it('should render list with nested object', () => {
const field = fromJS({
name: 'list',
label: 'List',
field: {
name: 'object',
widget: 'object',
label: 'Object',
fields: [{ name: 'title', widget: 'string', label: 'Title' }],
},
});
const { asFragment, getByTestId } = render(
<ListControl
{...props}
field={field}
value={fromJS([{ object: { title: 'item 1' } }, { object: { title: 'item 2' } }])}
/>,
);

expect(getByTestId('styled-list-item-top-bar-0')).toHaveAttribute('collapsed', 'true');
expect(getByTestId('styled-list-item-top-bar-1')).toHaveAttribute('collapsed', 'true');

expect(getByTestId('object-control-0')).toHaveAttribute('collapsed', 'true');
expect(getByTestId('object-control-1')).toHaveAttribute('collapsed', 'true');

expect(asFragment()).toMatchSnapshot();
});

it('should render list with nested object with collapse = false', () => {
const field = fromJS({
name: 'list',
label: 'List',
collapsed: false,
field: {
name: 'object',
widget: 'object',
label: 'Object',
fields: [{ name: 'title', widget: 'string', label: 'Title' }],
},
});
const { asFragment, getByTestId } = render(
<ListControl
{...props}
field={field}
value={fromJS([{ object: { title: 'item 1' } }, { object: { title: 'item 2' } }])}
/>,
);

expect(getByTestId('styled-list-item-top-bar-0')).toHaveAttribute('collapsed', 'false');
expect(getByTestId('styled-list-item-top-bar-1')).toHaveAttribute('collapsed', 'false');

expect(getByTestId('object-control-0')).toHaveAttribute('collapsed', 'false');
expect(getByTestId('object-control-1')).toHaveAttribute('collapsed', 'false');

expect(asFragment()).toMatchSnapshot();
});

it('should collapse all items on top bar collapse click', () => {
const field = fromJS({
name: 'list',
label: 'List',
collapsed: false,
field: {
name: 'object',
widget: 'object',
label: 'Object',
fields: [{ name: 'title', widget: 'string', label: 'Title' }],
},
});
const { getByTestId } = render(
<ListControl
{...props}
field={field}
value={fromJS([{ object: { title: 'item 1' } }, { object: { title: 'item 2' } }])}
/>,
);

expect(getByTestId('styled-list-item-top-bar-0')).toHaveAttribute('collapsed', 'false');
expect(getByTestId('styled-list-item-top-bar-1')).toHaveAttribute('collapsed', 'false');

expect(getByTestId('object-control-0')).toHaveAttribute('collapsed', 'false');
expect(getByTestId('object-control-1')).toHaveAttribute('collapsed', 'false');

fireEvent.click(getByTestId('expand-button'));

expect(getByTestId('styled-list-item-top-bar-0')).toHaveAttribute('collapsed', 'true');
expect(getByTestId('styled-list-item-top-bar-1')).toHaveAttribute('collapsed', 'true');

expect(getByTestId('object-control-0')).toHaveAttribute('collapsed', 'true');
expect(getByTestId('object-control-1')).toHaveAttribute('collapsed', 'true');
});

it('should collapse a single item on collapse item click', () => {
const field = fromJS({
name: 'list',
label: 'List',
collapsed: false,
field: {
name: 'object',
widget: 'object',
label: 'Object',
fields: [{ name: 'title', widget: 'string', label: 'Title' }],
},
});
const { getByTestId } = render(
<ListControl
{...props}
field={field}
value={fromJS([{ object: { title: 'item 1' } }, { object: { title: 'item 2' } }])}
/>,
);

expect(getByTestId('styled-list-item-top-bar-0')).toHaveAttribute('collapsed', 'false');
expect(getByTestId('styled-list-item-top-bar-1')).toHaveAttribute('collapsed', 'false');

expect(getByTestId('object-control-0')).toHaveAttribute('collapsed', 'false');
expect(getByTestId('object-control-1')).toHaveAttribute('collapsed', 'false');

fireEvent.click(getByTestId('styled-list-item-top-bar-0'));

expect(getByTestId('styled-list-item-top-bar-0')).toHaveAttribute('collapsed', 'true');
expect(getByTestId('styled-list-item-top-bar-1')).toHaveAttribute('collapsed', 'false');

expect(getByTestId('object-control-0')).toHaveAttribute('collapsed', 'true');
expect(getByTestId('object-control-1')).toHaveAttribute('collapsed', 'false');
});

it('should expand all items on top bar expand click', () => {
const field = fromJS({
name: 'list',
label: 'List',
collapsed: true,
field: {
name: 'object',
widget: 'object',
label: 'Object',
fields: [{ name: 'title', widget: 'string', label: 'Title' }],
},
});
const { getByTestId } = render(
<ListControl
{...props}
field={field}
value={fromJS([{ object: { title: 'item 1' } }, { object: { title: 'item 2' } }])}
/>,
);

expect(getByTestId('styled-list-item-top-bar-0')).toHaveAttribute('collapsed', 'true');
expect(getByTestId('styled-list-item-top-bar-1')).toHaveAttribute('collapsed', 'true');

expect(getByTestId('object-control-0')).toHaveAttribute('collapsed', 'true');
expect(getByTestId('object-control-1')).toHaveAttribute('collapsed', 'true');

fireEvent.click(getByTestId('expand-button'));

expect(getByTestId('styled-list-item-top-bar-0')).toHaveAttribute('collapsed', 'false');
expect(getByTestId('styled-list-item-top-bar-1')).toHaveAttribute('collapsed', 'false');

expect(getByTestId('object-control-0')).toHaveAttribute('collapsed', 'false');
expect(getByTestId('object-control-1')).toHaveAttribute('collapsed', 'false');
});

it('should expand a single item on expand item click', () => {
const field = fromJS({
name: 'list',
label: 'List',
collapsed: true,
field: {
name: 'object',
widget: 'object',
label: 'Object',
fields: [{ name: 'title', widget: 'string', label: 'Title' }],
},
});
const { getByTestId } = render(
<ListControl
{...props}
field={field}
value={fromJS([{ object: { title: 'item 1' } }, { object: { title: 'item 2' } }])}
/>,
);

expect(getByTestId('styled-list-item-top-bar-0')).toHaveAttribute('collapsed', 'true');
expect(getByTestId('styled-list-item-top-bar-1')).toHaveAttribute('collapsed', 'true');

expect(getByTestId('object-control-0')).toHaveAttribute('collapsed', 'true');
expect(getByTestId('object-control-1')).toHaveAttribute('collapsed', 'true');

fireEvent.click(getByTestId('styled-list-item-top-bar-0'));

expect(getByTestId('styled-list-item-top-bar-0')).toHaveAttribute('collapsed', 'false');
expect(getByTestId('styled-list-item-top-bar-1')).toHaveAttribute('collapsed', 'true');

expect(getByTestId('object-control-0')).toHaveAttribute('collapsed', 'false');
expect(getByTestId('object-control-1')).toHaveAttribute('collapsed', 'true');
});
});

0 comments on commit 0504c58

Please sign in to comment.