[英]Resolve location dependency warning in React useEffect hook
I have a useEffect
that I would like to execute only the first time in a React component.我有一个
useEffect
,我只想在 React 组件中第一次执行。 I am using location.pathname
in the useEffect
, if I leave the array dependencies empty, I get this warning:我在
useEffect
中使用location.pathname
,如果我将数组依赖项留空,我会收到此警告:
React Hook useEffect has a missing dependency: 'location.pathname'. Either include it or remove the dependency array.eslintreact-hooks/exhaustive-deps
If I include the dependency, useEffect
will be executed each time the user navigates.如果我包含依赖项,则每次用户导航时都会执行
useEffect
。
I see many people telling that the warning is just a potential problem, but if you know what you are doing, you can just simply ignore it, or disable the warning with // eslint-disable-line react-hooks/exhaustive-deps
.我看到很多人说这个警告只是一个潜在的问题,但如果你知道自己在做什么,你可以简单地忽略它,或者使用
// eslint-disable-line react-hooks/exhaustive-deps
禁用警告。
I have been reading about this problem, I know that for functions I should use useCallback
.我一直在阅读这个问题,我知道对于函数我应该使用
useCallback
。 What would be the equivalent for this case?这种情况的等价物是什么?
import { useLocation } from 'react-router-dom';
// Inside component
const location = useLocation();
useEffect(() => {
if (location.pathname === VIEWS.initial) {
setChecked(false);
}
}, []);
What would be the most correct solution to this problem?这个问题最正确的解决方案是什么?
I would recommend setting the initial value in useState
instead of useEffect
:我建议在
useState
而不是useEffect
中设置初始值:
const location = useLocation();
const [checked, setChecked] = useState(location.pathname === VIEWS.initial)
If you really want to set the state on mount via useEffect
, the least verbose alternative would be to suppress the warning with a comment.如果您真的想通过
useEffect
将 state 设置为挂载,最不冗长的替代方法是通过注释抑制警告。 However, if you at a later point extend this effect with more logic, you run the risk of encountering cryptic bugs regarding stale data that this warning might have prevented.但是,如果您稍后使用更多逻辑扩展此效果,您将面临遇到有关此警告可能已阻止的陈旧数据的神秘错误的风险。
The third way would be to make sure that the effect is only run once while keeping the location.pathname
dependency:第三种方法是确保效果仅运行一次,同时保持
location.pathname
依赖性:
const [hasMounted, setHasMounted] = useState(false)
const location = useLocation();
useEffect(() => {
if (!hasMounted && location.pathname === VIEWS.initial) {
setChecked(false);
setHasMounted(true);
}
}, [location.pathname, hasMounted]);
This is in my opinion not advisable because of poor readability and unnecessary complexity compared to my first suggestion.与我的第一个建议相比,我认为这是不可取的,因为可读性差且不必要的复杂性。
Solved with useRef
.用
useRef
解决。 It seems working fine, warning disappeared:看起来工作正常,警告消失了:
import { useLocation } from 'react-router-dom';
import { useRef } from 'react';
// Inside component
const location = useLocation();
const initialView = useRef(location.pathname);
useEffect(() => {
if (initialView.current === VIEWS.initial) {
setChecked(false);
}
}, []);
const location = useLocation();
useEffect(() => {
if ((location.pathname)&&location.pathname === VIEWS.initial) {
setChecked(false);
}
}, []);
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.