Реакционные крючки Eslint / полная рекурсия - PullRequest
1 голос
/ 03 марта 2020

Мне нужна помощь, чтобы обернуть голову вокруг eslint react-hooks/exhaustive derps. Я ТОЛЬКО хочу, чтобы эффект запускался, когда listenToMe изменился, но react-hooks/exhaustive derps кричит на меня, чтобы добавить history. Это вызывает рекурсию. useEffect было React gold для меня до этого правила.

ESLint: React Hook useEffect не имеет зависимостей: 'history'. Либо включите их, либо удалите массив зависимостей. (Reaction-hooks / исчерпывающий-deps)

Может кто-нибудь помочь мне понять:

  1. Почему плохая практика - слушать только для изменений, которые вас интересуют в использованииEffect? ​​
  2. Каков "правильный" способ прослушивания только определенных c изменений при изменении состояния?
  useEffect(() => {
    if (listenToMe) {
        const search = new URLSearchParams(location.search);
        search.delete('q')
        history.replace({ ...location, search: search.toString() });
      }
    }
  }, [listenToMe]);

Я прочитал через github и реагировать, но я не читал ничего, что щелкает.

Ответы [ 3 ]

0 голосов
/ 10 марта 2020

React отключил автофиксатор https://github.com/facebook/react/issues/15204

Я установил новый devDependancies (eslint@latest и eslint-plugin-react-hooks)

npm install eslint@latest eslint-plugin-react-hooks@latest --save-dev 

Я протестировал в IntelliJ IDEA 2020.1 (EAP Build # IU-201.5985.32) и показывает предупреждение , но ESLint Fix не добавляет автоматически зависимости в useEffect

Предупреждение ESLint в IntelliJ

ESLint: React Hook useEffect отсутствует зависимость: 'dispatch'. Либо включите его, либо удалите массив зависимостей. Если «dispatch» изменяется слишком часто, найдите родительский компонент, который его определяет, и включите это определение в useCallback. (Act-hooks / исчерпывающее-deps)

В коде VS есть «исправление» в предварительной версии 2.1.0-next.1, но я его не проверял.

https://github.com/microsoft/vscode-eslint/pull/814#issuecomment -587020489 https://github.com/microsoft/vscode-eslint/releases/tag/release%2F2.1.0-next.1

Это НЕ отвечает на вопрос, но помогает всем, кто сталкивается с react-hooks/exhaustive-deps авто "исправлением" проблем.

0 голосов
/ 05 мая 2020

Из документов

Опускать функцию из списка зависимостей безопасно только в том случае, если в нем (или вызываемых им функциях) нет ссылок на реквизиты, состояние или значения, полученные из них.

Проблема возникает, когда вы используете пропущенные реквизиты или, в вашем случае, реквизит истории, исходящий из HO C или хука от реакции-маршрутизатора.

Прежде всего , он передается как реквизит, и реквизит может измениться.

Во-вторых, вы вызываете функцию history.pu sh. Линтер не знает, что pu sh всегда будет одной и той же функцией класса истории, и что эта функция не будет использовать никакое состояние или подставлять себя.

«Правильный» путь согласно Facebook - это переместите функцию внутрь эффекта, но это не имеет смысла, если вы просто повторно используете код из какого-либо файла или используете функцию, подобную history.pu sh. Поэтому я думаю, что в вашем случае решение было бы заключить его в useCallback с историей в свой собственный массив зависимостей. Это последнее средство в соответствии с разработчиками.

По сути, useCallback просто возвращает запомненное значение вместо фактического доступа к значению, и всякий раз, когда значение в его зависимости изменяется, возникает новый обратный вызов с новыми запомненными значениями.

History.pu sh, конечно, всегда будет иметь одну и ту же идентичность, так что это отчасти противоречит закону.

Лично у меня никогда не было проблем с передачей таких значений. Поэтому я думаю, что писать useCallback, когда вы просто имеете дело с функциями, объявленными в другом месте (или любой полностью стабильной переменной), бессмысленно, и я считаю разумным пропустить ограничение этой строки.

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

0 голосов
/ 04 марта 2020

Это правило eslint является лишь подсказкой, полезной в большинстве ситуаций, но в некоторых ситуациях его следует игнорировать.

React.useEffect(()=> {

  // I have some code with dependencies here but I only want to run it on mount

// eslint-disable-next-line react-hooks/exhaustive-deps
}, [])
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...