【问题标题】:React Testing Library / React RouterReact 测试库/React 路由器
【发布时间】:2021-04-01 15:45:14
【问题描述】:

我正在尝试测试我的登录页面,以在对 API 进行 200 次调用后验证它是否会重定向到我们的仪表板。

import { render as testRender } from '@testing-library/react';
import { ThemeProvider, Global } from '@emotion/react';
import { MemoryRouter } from 'react-router-dom';
import UserContext from '../user.context';
import { theme } from '../theme/theme';
import { globalStyles } from '../theme/globalstyles';

export const render = (component) => {
    return testRender(
        <UserContext.Provider value={{firstName: 'John', lastName: 'Doe'}}>
            <ThemeProvider theme={theme}>
                <Global styles={globalStyles} />
                <MemoryRouter>{component}</MemoryRouter>
            </ThemeProvider>
        </UserContext.Provider>
    )
}

我的测试是插入电子邮件/密码并点击登录按钮

test('Mock signin call and verify you get taken to overview page', async () => {        
    render(<SignIn />);

    userEvent.type(screen.getByTestId('input-email'), 'john.wayne@sifted.com');
    userEvent.type(screen.getByTestId('input-password'), 'HowdyP1lgrum!');
    fireEvent.click(screen.getByTestId('button-signin'));

    await screen.findByText('user-name');
    expect(screen.getByText(/John Wayne/i)).toBeInTheDocument();
});

我的 Signin.jsx 中有代码,用于查找已完成表单的状态,并使用来自 React Router Dom 的 &lt;Redirect/&gt; 来转换页面。

if (status.state === FORMSTATUS.COMPLETED) {
    if (status.resetPassword) {
        return <Redirect to={{ pathname: ROUTES.UPDATEPASSWORD, state: { email: credentials.email } }} />
    } else {
        console.log('************** Got Here ****************');
        return <Redirect to={ROUTES.OVERVIEW} />
    }
}

我可以看到记录的语句****Got Here*** 但是它永远不会在登录用户的标题中找到 DOM。重定向似乎永远不会触发,我被 &lt;body&gt;&lt;div /&gt;&lt;/body&gt; 卡住了。

我是否在设置中遗漏了一些东西来正确测试路由转换?

【问题讨论】:

    标签: reactjs react-router react-testing-library


    【解决方案1】:

    您可以将自定义渲染更改为:

    //other imports
    import { Router } from "react-router-dom";
    import { createMemoryHistory } from "history";
    
    export function render(
      component,
      {
        route = "/",
        history = createMemoryHistory({
          initialEntries: [route]
        }),
        ...options
      } = {}
    ) {
      const messages = resourceConvertor(resource);
      const userContext = createUserContext({});
    
      function wrapper({ children }) {
        return (
          <UserContext.Provider value={{ firstName: "John", lastName: "Doe" }}>
            <ThemeProvider theme={theme}>
              <Global styles={globalStyles} />
              <Router history={history}>{children}</Router>
            </ThemeProvider>
          </UserContext.Provider>
        );
      }
    
      return {
        ...testRender(component, { wrapper, ...options }),
        history
      };
    }
    
    

    现在您可以查看历史记录,看看它是否是您想要的路线:

    test("Mock signin call and verify you get taken to overview page", async () => {
      const { history } = render(<SignIn />);
    
      userEvent.type(screen.getByTestId("input-email"), "john.wayne@sifted.com");
      userEvent.type(screen.getByTestId("input-password"), "HowdyP1lgrum!");
      fireEvent.click(screen.getByTestId("button-signin"));
    
      // I don't know about these two line, usually you want to mock exteranl api call
      await screen.findByText("user-name");
      expect(screen.getByText(/John Wayne/i)).toBeInTheDocument();
    
      // now check to see if the url has bee redirected or not
      expect(history.location.pathname).toBe(ROUTES.OVERVIEW)
    });
    

    【讨论】:

      猜你喜欢
      • 2021-01-09
      • 2022-07-14
      • 2020-08-28
      • 1970-01-01
      • 2021-06-14
      • 1970-01-01
      • 2021-05-25
      • 2021-10-11
      • 2018-12-27
      相关资源
      最近更新 更多