Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Migrated DateField tests to @testing-library/react #1340

Merged
merged 14 commits into from
Jun 21, 2024
195 changes: 60 additions & 135 deletions packages/uniforms-antd/__tests__/DateField.tsx
Original file line number Diff line number Diff line change
@@ -1,149 +1,74 @@
import DatePicker from 'antd/lib/date-picker';
import { screen } from '@testing-library/react';
import userEvent, {
PointerEventsCheckLevel,
} from '@testing-library/user-event';
import moment from 'moment';
import React from 'react';
import { DateField } from 'uniforms-antd';

import createContext from './_createContext';
import mount from './_mount';

test('<DateField> - renders an input', () => {
const element = <DateField name="x" />;
const wrapper = mount(element, createContext({ x: { type: Date } }));

expect(wrapper.find(DatePicker)).toHaveLength(1);
});

test('<DateField> - default props override', () => {
const pickerProps = { showTime: false, style: {} };
const element = <DateField name="x" {...pickerProps} />;
const wrapper = mount(element, createContext({ x: { type: Date } }));

expect(wrapper.find(DatePicker).props()).toEqual(
expect.objectContaining(pickerProps),
);
import { renderWithZod } from 'uniforms/__suites__';
import { z } from 'zod';

const getClosestInput = (text: string) =>
screen.getByText(text).closest('.ant-row')?.querySelector('input');

test('<DateField> - default props override', async () => {
const pickerProps = { showTime: false, style: { background: 'red' } };
renderWithZod({
element: <DateField name="x" {...pickerProps} />,
schema: z.object({ x: z.date() }),
piotrpospiech marked this conversation as resolved.
Show resolved Hide resolved
});
const body = screen.getByText('X').closest('body');
const input = body?.querySelector('.ant-picker');
expect(input).toBeInTheDocument();
expect(input).toHaveStyle('background: red');

await userEvent.click(input!);
expect(body?.querySelector('.ant-picker-time-panel')).not.toBeInTheDocument();
});

test('<DateField> - renders a input with correct id (inherited)', () => {
const element = <DateField name="x" />;
const wrapper = mount(element, createContext({ x: { type: Date } }));

expect(wrapper.find(DatePicker)).toHaveLength(1);
expect(wrapper.find(DatePicker).prop('id')).toBeTruthy();
});

test('<DateField> - renders a input with correct id (specified)', () => {
const element = <DateField name="x" id="y" />;
const wrapper = mount(element, createContext({ x: { type: Date } }));

expect(wrapper.find(DatePicker)).toHaveLength(1);
expect(wrapper.find(DatePicker).prop('id')).toBe('y');
});

test('<DateField> - renders a input with correct name', () => {
const element = <DateField name="x" />;
const wrapper = mount(element, createContext({ x: { type: Date } }));

expect(wrapper.find(DatePicker)).toHaveLength(1);
expect(wrapper.find(DatePicker).prop('name')).toBe('x');
});

test('<DateField> - renders an input with correct disabled state', () => {
const element = <DateField name="x" disabled />;
const wrapper = mount(element, createContext({ x: { type: Date } }));

expect(wrapper.find(DatePicker)).toHaveLength(1);
expect(wrapper.find(DatePicker).prop('disabled')).toBe(true);
});

test('<DateField> - renders an input with correct readOnly state', () => {
test('<DateField> - renders a input which correctly reacts on change (empty)', async () => {
const onChange = jest.fn();

const now = moment();
const element = <DateField name="x" readOnly />;
const wrapper = mount(
element,
createContext({ x: { type: Date } }, { onChange }),
);

expect(wrapper.find(DatePicker)).toHaveLength(1);
// @ts-expect-error
expect(wrapper.find(DatePicker).prop('onChange')(now)).toBeFalsy();
expect(onChange).not.toHaveBeenCalled();
});

test('<DateField> - renders a input with correct label (specified)', () => {
const element = <DateField name="x" label="DateFieldLabel" />;
const wrapper = mount(element, createContext({ x: { type: Date } }));

expect(wrapper.find('label')).toHaveLength(1);
expect(wrapper.find('label').text()).toBe('DateFieldLabel');
});

test('<DateField> - renders a input with correct value (default)', () => {
const element = <DateField name="x" />;
const wrapper = mount(element, createContext({ x: { type: Date } }));

expect(wrapper.find(DatePicker)).toHaveLength(1);
expect(wrapper.find(DatePicker).prop('value')).toBe(undefined);
});

test('<DateField> - renders a input with correct value (model)', () => {
const now = moment();
const element = <DateField name="x" />;
const wrapper = mount(
element,
createContext({ x: { type: Date } }, { model: { x: now } }),
);

expect(wrapper.find(DatePicker)).toHaveLength(1);
expect(wrapper.find(DatePicker).prop('value')).toEqual(now);
});

test('<DateField> - renders a input with correct value (specified)', () => {
const now = moment();
const element = <DateField name="x" value={now} />;
const wrapper = mount(element, createContext({ x: { type: Date } }));

expect(wrapper.find(DatePicker)).toHaveLength(1);
expect(wrapper.find(DatePicker).prop('value')).toEqual(now);
renderWithZod({
element: <DateField name="x" value={new Date()} />,
onChange,
schema: z.object({ x: z.date() }),
});

const input = getClosestInput('X');
expect(input).toBeInTheDocument();
await userEvent.click(input!);
const clear = input?.parentElement?.querySelector('.ant-picker-clear');
await userEvent.click(clear!);
expect(onChange).toHaveBeenLastCalledWith('x', undefined);
});

test('<DateField> - renders a input which correctly reacts on change', () => {
test('<DateField> - renders a input which correctly reacts on change', async () => {
const onChange = jest.fn();

const now = moment();
const element = <DateField name="x" />;
const wrapper = mount(
element,
createContext({ x: { type: Date } }, { onChange }),
);

expect(wrapper.find(DatePicker)).toHaveLength(1);
// @ts-expect-error
expect(wrapper.find(DatePicker).prop('onChange')(now)).toBeFalsy();
const now = moment('2024-01-01 12:00:00');
renderWithZod({
element: <DateField name="x" />,
onChange,
schema: z.object({ x: z.date() }),
});

const input = getClosestInput('X');
expect(input).toBeInTheDocument();
await userEvent.click(input!);
await userEvent.type(input!, now.format('YYYY-MM-DD HH:mm:ss'));
const ok = screen.getByText('Ok');
await userEvent.click(ok, {
pointerEventsCheck: PointerEventsCheckLevel.Never,
});
expect(onChange).toHaveBeenLastCalledWith('x', now.toDate());
});

test('<DateField> - renders a input which correctly reacts on change (empty)', () => {
const onChange = jest.fn();

const element = <DateField name="x" />;
const wrapper = mount(
element,
createContext({ x: { type: Date } }, { onChange }),
);

expect(wrapper.find(DatePicker)).toHaveLength(1);
// @ts-expect-error
expect(wrapper.find(DatePicker).prop('onChange')(undefined)).toBeFalsy();
expect(onChange).toHaveBeenLastCalledWith('x', undefined);
});

test('<DateField> - renders a wrapper with unknown props', () => {
const element = <DateField name="x" data-x="x" data-y="y" data-z="z" />;
const wrapper = mount(element, createContext({ x: { type: Date } }));

expect(wrapper.find(DatePicker).prop('data-x')).toBe('x');
expect(wrapper.find(DatePicker).prop('data-y')).toBe('y');
expect(wrapper.find(DatePicker).prop('data-z')).toBe('z');
renderWithZod({
element: <DateField name="x" data-x="x" data-y="y" data-z="z" />,
schema: z.object({ x: z.date() }),
});
const input = getClosestInput('X');
expect(input?.getAttribute('data-x')).toBe('x');
expect(input?.getAttribute('data-y')).toBe('y');
expect(input?.getAttribute('data-z')).toBe('z');
});
3 changes: 3 additions & 0 deletions packages/uniforms-antd/__tests__/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -64,6 +64,9 @@ describe('@RTL AntD', () => {
suites.testSelectField(theme.SelectField, { theme: 'antd' });
suites.testTextField(theme.TextField);
suites.testValidatedForm(theme.ValidatedForm);
suites.testDateField(theme.DateField, {
theme: 'antd',
});
suites.testValidatedQuickForm(theme.ValidatedQuickForm);
suites.testWrapField(theme.wrapField, {
helpPropsName: 'help',
Expand Down
45 changes: 24 additions & 21 deletions packages/uniforms-mui/__tests__/DateField.tsx
Original file line number Diff line number Diff line change
@@ -1,31 +1,34 @@
import FormHelperText from '@mui/material/FormHelperText';
import { screen } from '@testing-library/react';
import React from 'react';
import { DateField } from 'uniforms-mui';

import createContext from './_createContext';
import mount from './_mount';
import { renderWithZod } from 'uniforms/__suites__';
import { z } from 'zod';

test('<DateField> - renders a Input with correct error text (specified)', () => {
const error = new Error();
const element = (
<DateField name="x" error={error} showInlineError errorMessage="Error" />
);
const wrapper = mount(element, createContext({ x: { type: Date } }));

expect(wrapper.find(FormHelperText).text()).toBe('Error');
renderWithZod({
element: (
<DateField name="x" error={error} errorMessage="Error" showInlineError />
),
schema: z.object({ x: z.date() }),
});
expect(screen.getByText('Error')).toBeInTheDocument();
});

test('<DateField> - renders a Input with correct error text (showInlineError=false)', () => {
const error = new Error();
const element = (
<DateField
name="x"
error={error}
showInlineError={false}
errorMessage="Error"
/>
);
const wrapper = mount(element, createContext({ x: { type: Date } }));

expect(wrapper.find(FormHelperText)).toHaveLength(0);
renderWithZod({
element: (
<DateField
name="x"
error={error}
errorMessage="Error"
showInlineError={false}
/>
),
schema: z.object({ x: z.date() }),
});
expect(
screen.getByText('X').nextElementSibling?.classList.contains('Mui-error'),
).toBe(true);
});
Loading
Loading