反应 useMemo 缺少依赖项

时间:2021-04-28 14:13:05

标签: reactjs react-hooks

  const handleTestDelete = (id: any) => {
    deleteTest(id).then(() => {
      queryClient.invalidateQueries("test");
    });
  };

  const columns = useMemo(
    () => [
      { field: "id", headerName: "ID", width: 80 },
      {
        field: "",
        width: 120,
        disableClickEventBubbling: true,
        sortable: false,
        disableColumnMenu: true,
        renderCell: (cell: any) => (
          <>
            <IconButton
              aria-label="delete"
              onClick={() => handleTestDelete(cell.id)}
            >
              <DeleteIcon fontSize="small" />
            </IconButton>
            <IconButton
              aria-label="view"
              onClick={() => history.push(`/something/${cell.id}/details`)}
            >
              <VisibilityIcon fontSize="small" />
            </IconButton>
          </>
        ),
      },
    ],
    [history]

我收到此警告

<块引用>

React Hook useMemo 缺少依赖项:'handleTestDelete'。包括它或删除依赖项数组。

因为我没有添加在依赖项中单击删除按钮时调用的函数......为什么我要把它作为依赖项?我什至不确定将历史作为依赖项是否正确;我认为当年表发生变化时不需要重新评估列

我错了吗?

谢谢

1 个答案:

答案 0 :(得分:2)

如果您使用的是 useMemo,您应该满足 eslint-plugin-react-hooks 建议的依赖项:

const history = useHistory()

const columns = useMemo(() => {
  console.log("define memoized columns") // Log 1
  return [
    { field: 'id', headerName: 'ID', width: 80 },
    {
      // ... code here
      renderCell: (cell: any) => (
        <>
          <IconButton
            aria-label="delete"
            onClick={() => handleTestDelete(cell.id)}
          >
            <DeleteIcon fontSize="small" />
          </IconButton>
          <IconButton
            aria-label="view"
            onClick={() => history.push(`/something/${cell.id}/details`)}
          >
            <VisibilityIcon fontSize="small" />
          </IconButton>
        </>
      ),
    },
  ]
}, [history, handleTestDelete])

使用 history 是安全的,因为它不会改变(除非它在 ​​React Router 的上下文中改变,这在本例中是不可能的)。而且,您需要将该函数包装在 useCallback 中:

const handleTestDelete = useCallback((id: any) => {
  deleteTest(id).then(() => {
    queryClient.invalidateQueries('test')
  })
}, []) // <---- Here, you need to add the dependencies as well (maybe queryClient)

这里您可能还有一个选择:从 handleTestDelete 的依赖项中删除 useMemo,并在 handleTestDelete 中定义 useMemo 函数;在返回记忆化的列之前。

注意:由于我没有看到您的完整代码,我建议您测试此代码并确保正确打印 useMemo 中的 Log 1(仅打印一次) .


类似帖子: