30

I have a react component with a useEffect hook that looks like this:

const LocationEditor: React.FC<SectionEditorProps> = (props) => {
const [section, setSection] = useState({...(props.section as Location)});
useEffect(() => {
    props.onChange(section);
}, [section]);

I'm getting this warning when I run the project:

React Hook useEffect has a missing dependency: 'props'. Either include it or remove the dependency array. However, 'props' will change when *any* prop changes, so the preferred fix is to destructure the 'props' object outside of the useEffect call and refer to those specific props inside useEffect  react-hooks/exhaustive-deps

So I tried changing the component to look like this, destructuring props:

const LocationEditor: React.FC<SectionEditorProps> = ({section, onClickCancel, onClickSave, onChange}) => {
    const [tmpSection, setSection] = useState({...(section as Location)});
    useEffect(() => {
        onChange(tmpSection);      
    }, [tmpSection]);

If I add this comment before the dependency array, I can make the warning go away:

// eslint-disable-next-line react-hooks/exhaustive-deps

However, when I add the block below to eslintConfig in package.json it doesn't seem to do anything:

{
  "plugins": [
    "react-hooks"
  ],
  "rules": {
    "react-hooks/rules-of-hooks": "error",
    "react-hooks/exhaustive-deps": "off"
  }
}

I see some people talking about using the .eslinrc file, but I thought you could also configure rules globally in package.json and I can't find that file in my project.

Is there something I'm missing here?

master_chef
  • 345
  • 1
  • 3
  • 9
  • 5
    That is almost certainly a [bad idea](https://kentcdodds.com/blog/react-hooks-pitfalls). Just put the `onChange` function in your dependency array. Why is everybody's response to the tool, that *React team at Facebook itself uses*, telling them that they're possibly doing something wrong to immediately want to toss out the tool? I realize it's not just you, we get this question in the react tag all the time, it just never fails to surprise me... – Jared Smith Jan 13 '21 at 15:12
  • Thanks! That was helpful. Basically I fixed it like this: https://stackoverflow.com/questions/58866796/understanding-the-react-hooks-exhaustive-deps-lint-rule – master_chef Jan 13 '21 at 16:28
  • 3
    Acknowledging that it's a bad idea to disable this rule, it would still be nice to have an answer to this question for those of us who are stubborn. The linked answer does not address the problem of the package.json config seemingly being ignored. – Mike Willis Apr 06 '21 at 18:52
  • This answer helped me a lot (ignoring warning): https://stackoverflow.com/questions/63974832/how-to-disable-react-hooks-exhaustive-deps-eslint-warning-globally – Roberto Fernandes Jul 02 '22 at 04:11
  • https://beta.reactjs.org/learn/removing-effect-dependencies#why-is-suppressing-the-dependency-linter-so-dangerous – Andreas Riedmüller Jan 25 '23 at 16:02

1 Answers1

20

Usually you don't want to disable the rule. However, there are few cases where it's worthwhile to disable it.

For example, if you're doing a fetch on mount and you're sure it never has to execute again, you can disable it with the code below.

// eslint-disable-next-line react-hooks/exhaustive-deps

First, confirm the rule is wrong. It has been battle tested and most of the time it'll be right. You can introduce subtle bugs by ignoring the dependencies.

You can also disable the rule globally, although that's not recommended.

Obed Parlapiano
  • 3,226
  • 3
  • 21
  • 39
  • 1
    thanks! Fixed it per the comment above. Appreciate your help. – master_chef Jan 13 '21 at 17:58
  • 55
    "Just do what the rule says" - it's not always the best option. An example: if you need to fetch data from a server, you usually pass to useEffect an empty array as a second argument (because you need to run the callback only once when your component did mount) - and it's an official advice from React documentation. And then "exhaustive-deps" often starts to annoy you with warnings that you "forgot" dependencies (but you're sure you didn't). And adding dependencies you don't need is an antipattern, because it may lead to unnecessary rerenderings or even to an infinite cycle of rerenderings... – Roman Karagodin Aug 29 '21 at 15:29
  • 3
    This is just partly true, I think. Actually, the official documentation for useState says that it is safe to omit the setter from the dependency array. https://reactjs.org/docs/hooks-reference.html#usestate Perhaps it is too much to expect from the linter to identify a setter or useReducer-dispatch function that is not included in the dependency array? – aweibell Jan 29 '22 at 12:41