Run useEffect Only Once

Avatar of Chris Coyier
Chris Coyier on

React has a built-in hook called useEffect. Hooks are used in function components. The Class component comparison to useEffect are the methods componentDidMount, componentDidUpdate, and componentWillUnmount.

useEffect will run when the component renders, which might be more times than you think. I feel like I’ve had this come up a dozen times in the past few weeks, so it seems worthy of a quick blog post.

import React, { useEffect } from 'react';

function App() {
  useEffect(() => {
    // Run! Like go get some data from an API.
  });

  return (
    <div>
      {/* Do something with data. */}
    </div>
  );
}

In a totally isolated example like that, it’s likely the useEffect will run only once. But in a more complex app with props flying around and such, it’s certainly not guaranteed. The problem with that is that if you’re doing something like fetching data from an API, you might end up double-fetching which is inefficient and unnecessary.

The trick is that useEffect takes a second parameter.

The second param is an array of variables that the component will check to make sure changed before re-rendering. You could put whatever bits of props and state you want in here to check against.

Or, put nothing:

import React, { useEffect } from 'react';

function App() {
  useEffect(() => {
    // Run! Like go get some data from an API.
  }, []);

  return (
    <div>
      {/* Do something with data. */}
    </div>
  );
}

That will ensure the useEffect only runs once.

Note from the docs:

If you use this optimization, make sure the array includes all values from the component scope (such as props and state) that change over time and that are used by the effect. Otherwise, your code will reference stale values from previous renders.