React Router 的 useParams 导致 useEffect 重新运行
Posted
技术标签:
【中文标题】React Router 的 useParams 导致 useEffect 重新运行【英文标题】:React Router's useParams cause useEffect to rerun 【发布时间】:2020-02-02 17:59:41 【问题描述】:我正在使用react-router
5.1 和react
16.10。
对于主从页面,我使用useParams()
从 url 获取 id 以打开当前组的页面。打开发生在useEffect()
。因此,id
必须作为该效果的依赖项。但是,当创建一个新组时,如果有足够的数据使组有效,API 会发送该组的 id
并将 URL 设置为 /group/:id
。结果,效果再次运行。
function Groups(props)
const id = useParams();
const history = useHistory();
const [group, setGroup] = useState(NEW_GROUP);
const getData = useCallback(async () =>
await Promise.resolve(Api.getGroups());
, []);
const getGroup = useCallback(async group =>
history.push(`/groups/$group.id`);
await Promise.resolve(Api.getGroup(group)).then(data =>
setGroup(data.group);
);
, [getData, history]);
useEffect(() =>
getData();
if (id !== undefined)
getGroup( id );
, [props.actions, id, getData, getGroup]);
// Saving data
const saveGroup = useCallback(async () =>
setSaved(SAVING);
await Promise.resolve(Api.storeGroup(group)).then(data =>
if (!group.hasOwnProperty('id'))
history.push(`/groups/$data.id`);
setGroup(prevGroup => ( ...prevGroup, id: data.id ));
getData();
setSaved(SAVED);
).catch(() => setSaved(FAILED));
, [getData, group, history]);
如何在不违反“钩子规则”的情况下防止这种情况发生?
【问题讨论】:
你想让useEffects只在id值改变时运行吗? 我只希望它第一次运行。通常这可以通过将依赖项数组留空来完成,但在这种情况下,这违反了“钩子规则”,我宁愿不包括 ESlin 的规则例外。 @Yannick 你解决过这个问题吗?我有完全相同的问题,将 useParams() 用于导致 useEffect 无限循环的对象 id。 我还没有找到合适的解决方案,我们现在根本不更改 URL。不过,这并不理想。 【参考方案1】:我遇到了同样的问题,我解决的方法是将 id 从 useParams 传递给函数并仅在 useEffect 中设置 id。
function Groups(props)
const id = useParams();
...
useEffect(() =>
getData(id);
if (id !== undefined)
getGroup( id );
, [id]);
...
【讨论】:
它对我有用,我使用 getGroup(id) 而不是 getGroup( id ); 在“react-router-dom”中相同:“^5.2.0”,我想知道为什么当 id 未定义时 useEffect 看到 id 发生了变化。似乎有些东西在 useParams()...以上是关于React Router 的 useParams 导致 useEffect 重新运行的主要内容,如果未能解决你的问题,请参考以下文章
类组件内的 react-router-dom useParams()
TypeError:使用来自 react-router 的 useParams 时无法读取未定义的属性“匹配”