userEvent.type(...) 应将哪个元素定位为与 MUI 的 DesktopDatePicker TextField 一起使用?

What element should userEvent.type(...) target to be used with MUI's DesktopDatePicker TextField?

如何使用 react-testing-library user-event type 到 MUI 日期选择器中的 TextField 输入?我可以看到正在应用遮罩

我试过 userEvent.type(inputEl, '1')userEvent.keyboard('1')。在这两种情况下,输入都为空。

我目前的假设是重新呈现用高阶组件的空状态替换我的更新(这是有道理的,基于输入的日期格式掩码的应用程序)。

documentation example works as expected, so my issue is specific to the MUI datepicker.

可以在此 sandbox.

中找到组件(和测试)的简化版本

下面是渲染的 HTML 的副本,以证明我使用 data-testid 定位输入元素,但它不起作用:

screen.getByTestId('date-selector-text-field').outerHTML:
<input
  aria-invalid="false"
  placeholder="dd / mm / yyyy"
  readonly=""
  type="text"
  aria-readonly="true"
  aria-label="Choose date"
  data-testid="date-selector-text-field"
  class="MuiOutlinedInput-input MuiInputBase-input css-1t8l2tu-MuiInputBase-input-MuiOutlinedInput-input"
  value=""
  aria-describedby="mui-1-helper-text"
  id="mui-1"
>

我添加了以下内容,以确保在测试中为桌面呈现 DatePicker。您可以在此处找到更多相关信息:https://github.com/mui/material-ui-pickers/issues/2073#issuecomment-671834179

beforeAll(() => {
    // add window.matchMedia
    // this is necessary for the date picker to be rendered in desktop mode.
    // if this is not provided, the mobile mode is rendered, which might lead to unexpected behavior
    Object.defineProperty(window, "matchMedia", {
      writable: true,
      value: (query: any) => ({
        media: query,
        // this is the media query that @material-ui/pickers uses to determine if a device is a desktop device
        matches: query === "(pointer: fine)",
        onchange: () => null,
        addEventListener: () => null,
        removeEventListener: () => null,
        addListener: () => null,
        removeListener: () => null,
        dispatchEvent: () => false,
      }),
    });
  });
  afterAll(() => {
    // eslint-disable-next-line @typescript-eslint/ban-ts-comment
    // @ts-ignore
    delete window.matchMedia;
  });

如果日期选择器中已有值,请在调用 userEvent.type() 时在 await userEvent.type() 前添加一个 await userEvent.clear()。 clear 是必需的,因为我们正在模拟实际的用户行为,如果你已经有一个值(我在我的测试用例中确实有),你就不能输入一些东西。