更新 NextJs 查询字符串时防止 useEffect 无限循环

Prevent useEffect infinite loop when updating NextJs query string

我有一个生成标签数组的标签输入。使用 NextJs 的 useRouter,我想在添加这些标签时将它们添加为查询字符串参数。我还需要保留当前的查询字符串参数,因为其他过滤器、搜索和分页需要保留。

这是我目前的做法。

const router = useRouter();
const { query } = router;
const [tags, setTags] = useState([]);

useEffect(() => {
  router.push({
    query: {
      ...query,
      tags,
    },
  });
}, [tags, router, query]);

return (
  <>
    <TagInput tags={tags} setTags={setTags} placeholder="Search by tags" />
  </>
);

但是,这会导致无限渲染,因为 useEffect 会更新 query 但也有 query 作为依赖项。如果我删除 query 作为依赖项,它工作正常,但我得到缺少的依赖项 linting 错误。

编辑:这是一个 codesandbox,其中包含一个可重现该问题的最小示例。它按原样工作,但如果你取消注释 query 依赖项,无限循环。 https://codesandbox.io/s/next-js-dynamic-routing-forked-rlxuqh?file=/pages/index.js

实现此目的的一种方法是直接更新查询对象并从 url 中读取标签,而不是将标签存储在状态中。

const router = useRouter();
const { query } = router;

const setTags = useCallback((tags) => {
  router.push({
    query: {
      ...query,
      tags
    }
  });
}, [router, query]);

return (
  <>
    <TagInput tags={query.tags || []} setTags={setTags} placeholder="Search by tags" />
  </>
);