2

如果我从中返回一个函数,useEffect我可以确定该函数将在组件卸载时运行。但是 React 似乎在调用我的卸载函数之前擦除了本地状态。

考虑一下:

function Component () {

  const [setting, setSetting] = useState(false)

  useEffect(() => {

    setSetting(true)

    // This should be called when unmounting component
    return () => {

      console.log('Send setting to server before component is unmounted')
      console.log(setting) // false (expecting setting to be true)
      
    }
  }, [])
  
  return (
    <p>Setting is: {setting ? 'true' : 'false'}</p>
  )
}

任何人都可以确认预期的行为是应该擦除组件状态吗?而且,如果这是正确的行为,如何在组件卸载之前将当前组件状态触发到服务器?

为了提供一些上下文,我正在对服务器的发布请求进行去抖动,以避免每次用户更改设置时触发它。去抖动效果很好,但是一旦用户离开页面,我需要一种方法来触发请求,因为排队的去抖动方法将不再从未安装的组件中触发。

4

1 回答 1

4

并不是说 React “消除了状态值”,而是你有关闭setting(挂载值)。

要获得预期的行为,您应该使用 aref和 anotheruseEffect来保持最新状态。

function Component() {
  const [setting, setSetting] = useState(false);

  const settingRef = useRef(setting);

  // Keep the value up to date
  // Use a ref to sync the value with component's life time
  useEffect(() => {
    settingRef.current = setting;
  }, [setting])
  

  // Execute a callback on unmount.
  // No closure on state value.
  useEffect(() => {
    const setting = settingRef.current;
    return () => {
      console.log(setting);
    };
  }, []);

  return <p>Setting is: {setting ? "true" : "false"}</p>;
}
于 2020-12-14T14:15:14.897 回答