繁体   English   中英

为什么 useFetcher 会导致重新渲染无限循环?

[英]Why is useFetcher causing an re-render infinite loop?

我有一个输入。 在每次更改输入时,我都想调用一个 API。

这是代码的简化版本:

  // updated by input
  const [urlText, setUrlText] = useState("");

  const fetcher = useFetcher();

  useEffect(() => {
    if (urlText === "" || !fetcher) return;
    fetcher.load(`/api/preview?url=${urlText}`);
  }, [urlText]);

问题是,当我将urlText放在依赖项数组中时,会出现无限渲染循环,而 React 声称问题是我可能正在更新useEffect内部的状态。 但是,据我所知,我没有更新钩子内的任何状态,所以我不确定为什么会发生无限重新渲染。

有什么想法吗?

代码的完整版本是:

注意:在没有去抖动或useMemo的情况下,该错误仍然会发生,所有这些内容大致无关紧要。

export default function () {
  const { code, higlightedCode } = useLoaderData<API>();

  const [urlText, setUrlText] = useState("");
  const url = useMemo(() => getURL(prefixWithHttps(urlText)), [urlText]);
  const debouncedUrl = useDebounce(url, 250);

  const fetcher = useFetcher();

  useEffect(() => {
    if (url === null || !fetcher) return;
    fetcher.load(`/api/preview?url=${encodeURIComponent(url.toString())}`);
  }, [debouncedUrl]);

  return (
             <input
            type="text"
            placeholder="Paste URL"
            className={clsx(
              "w-full rounded-sm bg-gray-800 text-white text-center placeholder:text-white"
              //"placeholder:text-left text-left"
            )}
            value={urlText}
            onChange={(e) => setUrlText(e.target.value)}
          ></input>
  );
}

您可以通过在useFetcher钩子中设置状态,请从useFetcher检查load方法的代码。

您遇到的问题是 fetcher 在整个提取过程中都会更新。 这导致您的效果重新运行,并且由于您再次调用load ,它正在重复循环。

您应该检查fetcher.state以查看何时获取。

useEffect(() => {
  // check to see if you haven't fetched yet
  // and we haven't received the data
  if (fetcher.state === 'idle' && !fetcher.data) {
    fetcher.load(url)
  }
}, [url, fetcher.state, fetcher.data])

https://remix.run/docs/en/v1/api/remix#usefetcher

更新:我很傻。 useDebounce返回一个数组。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM