useEffect Ленивая созданная функция очистки - PullRequest
3 голосов
/ 14 мая 2019

Я пытаюсь создать ловушку, которая использует эффект, при котором функция побочного эффекта возвращает обратный вызов очистки.Однако я хочу вызывать его только тогда, когда компонент отключен, а не при повторном отображении.

Обычный подход, когда вы вызываете useEffect с пустым массивом deps, здесь не сработает, поскольку функция очистки создается только один раз при первом вызове ловушки.Но моя очистка создается позже, поэтому изменить ее невозможно.


function useListener(data) {
  const [response, updateResponse] = useState(null);

  useEffect(
    () => {
      if (data) {
        const removeListener = callRequest(data, resp => {
          updateResponse(resp);
        });

        return removeListener;
      }
    },
    [data]
  );

  return response;
}

Это сводится к следующей проблеме: В обычном компоненте класса willComponentUnmount может принимать решение на основе текущего состояния компонента, но в случае useEffect состояние передается через замыкание в очистку.и нет никакой возможности передать информацию позже, если состояние изменилось

1 Ответ

1 голос
/ 14 мая 2019

Вы можете использовать useRef для сохранения и обновления функции обратного вызова

Хук useRef () предназначен не только для ссылок DOM.Объект «ref» - ​​это универсальный контейнер, текущее свойство которого является изменяемым и может содержать любое значение, подобное свойству экземпляра в классе. подробнее

function useListener(data) {
  const [response, updateResponse] = useState(null);
  const cleanUpCallbackRef = useRef(() => {});

  useEffect(
    () => {
      if (data) {
        cleanUpCallbackRef.current = callRequest(data, resp => {
          updateResponse(resp);
        });
      }
    },
    [data]
  );

  useEffect(() => {
    return () => {
      cleanUpCallbackRef.current();
    }
  }, []);
  return response;
}

Я создаю простой пример здесь

...