【问题标题】:Await for an element not to appear等待一个元素不出现
【发布时间】:2021-09-29 11:45:38
【问题描述】:

我需要编写一个测试,一旦权限 API 承诺得到解决,确保元素将不可见。

我已经基于the docs 编写了一个测试,但是它似乎只在元素最初存在时才有效。我的问题是元素('Test'字符串)不存在并且只要 userPermissions 不包含 requiredPermission 就不会存在,因此无论我是否通过正确的权限,测试都会通过。即使“测试”实际出现在页面上,测试expect(queryByText('Test')).not.toBeInTheDocument() 也通过了...

我想确定一个元素在我等待之后不会出现。

it('returns null if user does not have a permission', async () => {
  fetch.mockResponse(JSON.stringify({ read: false }));
  render(
    <PermissionsProvider>
      <HasPermission requiredPermission="read">Test</HasPermission>
    </PermissionsProvider>
  );

  await waitFor(() => {
    expect(queryByText('Test')).not.toBeInTheDocument()
  });
});

这是HasPermission 组件

export const HasPermission = ({ children, requiredPermission }) => {
  const { permissions: userPermissions } = useContext(PermissionsContext);

  const match = userPermissions.some(permission => requiredPermission);

  if (match) {
    return <>{children}</>;
  } else {
    return null;
  }
};

还有我的PermissionsProvider

const PermissionsContext = createContext(null);

export const PermissionsProvider = ({ children }) => {
  const [permissions, setPermissions] = useState({});

  useEffect(() => {
    const fetchPermissions = async () => {
      const response = await fetch('/permissions');
      setPermissions(response);
    };
    fetchPermissions();
  }, []);

  return (
    <PermissionsContext.Provider value={{ permissions }}>{children}</PermissionsContext.Provider>
  );
};

【问题讨论】:

  • 您确定获取的数据返回正确的信息吗?

标签: reactjs unit-testing jestjs react-testing-library


【解决方案1】:

渲染和更新 React 组件的代码需要包含在 React 的调用堆栈中。 React 测试库已经将 act 与其 API 集成。所以在大多数情况下,我们不需要将render 和fireEvent 包装在act 中。不过你可以试试:

act(()=> {
  render(
     <PermissionsProvider>
       <HasPermission requiredPermission="read">Test</HasPermission>
     </PermissionsProvider>
  );
});

但是阅读您的代码,我认为您的问题在这里:

const match = userPermissions.some(permission => requiredPermission);

因为 userPermissions 是 typeof Object 而不是 Array。您是否尝试将组件的权限与 userPermissions 中的某些属性相匹配?

 const match = userPermissions[requiredPermission];

【讨论】:

  • 我认为 waitFor 在幕后使用了 act
  • 是的,但有时你需要使用它,让我知道它是怎么回事
  • @ReturnOfTheMac 我认为这总是正确的-> const match = userPermissions.some(permission => requiredPermission);因为 requiredPermission 不是一个空字符串,并且您将 userPermissions 视为一个数组,但它是一个对象,我认为您的问题就在这里,您是否正在尝试类似 this-> const match = Object.entries(userPermissions).some( ([key, value])=> key === requiredPermission && value) ????
  • 是的,我认为显示组件的逻辑是错误的,所以测试正确通过。
  • 试试这个 const match = userPermissions[requiredPermission];
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2016-05-09
  • 2013-01-12
  • 2016-09-05
  • 1970-01-01
  • 2020-03-29
  • 1970-01-01
相关资源
最近更新 更多