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

时间:2020-08-01 09:08:58

标签: javascript reactjs react-hooks

我想添加setInterval以便能够从数据库中获取新数据而无需刷新页面,因此我使用useEffect,setInterval,useState来解决它,设置初始状态{refresh:false,refreshSells:null} 并且当刷新= true和refreshSells = setinterval()时有开关,但是我得到了烦人的警告 React Hook useEffect缺少依赖项:“ refreshSells”。包括它或删除依赖项数组 如果我添加refreshSells,它将是不可阻挡的循环

const Sells = () => {
        const [allSells,setAllSells] = useState([])
        const [refresh,setRefresh] = useState(false)
        const [refreshSells , setRefreshSells] = useState(null)
        const [hidden,setHidden] = useState(true)
        useEffect(() => {
            Axios.get('/sells')
            .then(({data}) => {
                setAllSells(data.sells)
            })
            .catch(() => {
                alert('something went wrong,ask omar')
            })
        },[])
        useEffect(() => {
            if(refresh){
                setRefreshSells(setInterval(() => {
                    Axios.get('/sells')
                    .then(({data}) => {
                        setAllSells(data.sells)
                    })
                }, 60000));
            }
            else{
                clearInterval(refreshSells)
            }
            return () => clearInterval(refreshSells)
        },[refresh])

3 个答案:

答案 0 :(得分:0)

setRefreshSells更新内部状态,并且在当前渲染期间不更改refreshSells。因此return () => clearInterval(refreshSells)将尝试清除错误的时间间隔。

您应该使用useRef挂钩作为间隔:

const refreshSellsRef = useRef(null);
...
useEffect(() => {
    if(refresh){
        refreshSellsRef.current = setInterval(() => {
            Axios.get('/sells')
            .then(({data}) => {
                setAllSells(data.sells)
            })
        }, 60000);
        return () => clearInterval(refreshSellsRef.current);
    }
},[refresh])

还要注意,return () => clearInterval(refreshSellsRef.current)将在卸载时和refresh更改时被调用。因此您不需要else {clearInterval(...)}

答案 1 :(得分:0)

如果您的业务逻辑允许将两种效果分开(每60秒自动刷新+单击某些按钮后手动刷新),则可以简化每种独立效果的代码:

    useEffect(() => {
        const interval = setInterval(() => {
            Axios.get('/sells')
            .then(({data}) => {
                setAllSells(data.sells)
            })
        }, 60000)
        return () => clearInterval(interval)
    }, [])

    useEffect(() => {
        if (refresh) {
            setRefresh(false)

            Axios.get('/sells')
            .then(({data}) => {
                setAllSells(data.sells)
            })
        };
    }, [refresh])

触发刷新后,您似乎忘记了setRefresh(false),但我不确定为什么首先需要refreshSells ...

答案 2 :(得分:0)

在第二个useEffect中,您将更新状态refreshSells,其中useEffect期望useCallback ref为依赖项。如果将refreshSells作为对useEffect的依赖项,则可能会遇到内存泄漏问题。

因此,我建议您尝试使用以下代码来解决您的问题。这样您还可以消除refreshSells

useEffect(() => {
    let interval;
    if (refresh) {
      interval = setInterval(() => {
         Axios.get('/sells')
          .then(({ data }) => {
            setAllSells(data.sells)
          });
      }, 4000);
    }
    return () => clearInterval(interval);
  }, [refresh]);