DEV Community

Cover image for Demystifying the useEffect Hook in React: A Beginner's Guide
Alfonsina Lizardo
Alfonsina Lizardo

Posted on

Demystifying the useEffect Hook in React: A Beginner's Guide

Today, we're diving into the useEffect hook, an essential tool in your React arsenal. Understanding the different ways to use useEffect will empower you to handle side effects and manage component lifecycles with confidence.


A reminder...

React components go through different stages during their existence, this is called the component lifecycle. These stages can be broadly categorized into three main phases:

  • Mounting: The component is created and inserted into the DOM
  • Updating: The component is re-rendered due to changes in its props or state
  • Unmounting: The component is removed from the DOM

In this blog post, we'll explore three main use cases of the useEffect hook: with an empty dependency array, with a dependency array with values and without a dependency array. Let's get started!

1. With an Empty Dependency Array

When you pass an empty dependency array to useEffect, it means the effect only runs once, when the component mounts. This is useful for performing one-time initializations or subscribing to events that don't change over time.

An use case for this can be fetching data from an API

import { useEffect, useState } from "react";

export default function App() {
  const [data, setData] = useState(null);

  useEffect(() => {
    fetch("https://mock-api.com")
      .then((response) => response.json())
      .then((apiData) => {
        setData(apiData);
      });
  }, []);

  return (
    <div>
      {data && data.message}
    </div>
  );
}
Enter fullscreen mode Exit fullscreen mode

In this example, the useEffect hook is used to fetch data from an API, the data is then set to the data state variable using the setData function. Since the dependency array is empty, this piece of code will only run once when the component is mounted.

2. With a Dependency Array with Values

When you provide a dependency array with specific values, the effect runs when the component is mounted AND when those values change. This allows you to respond to changes in the component's props or state selectively.

An use case for this could be a search functionality

import React, { useState, useEffect } from 'react';

function FilterableList({ items }) {
  const [filter, setFilter] = useState('');
  const [filteredItems, setFilteredItems] = useState(items);

  useEffect(() => {
    const filtered = items.filter(item => item.toLowerCase().includes(filter.toLowerCase()));
    setFilteredItems(filtered.length !== 0 ? filteredItems : items);
  }, [filter, items]);

  return (
    <div>
      <input type="text" value={filter} onChange={e => setFilter(e.target.value)} />
      <ul>
        {filteredItems.map(item => <li key={item}>{item}</li>)}
      </ul>
    </div>
  );
}
Enter fullscreen mode Exit fullscreen mode

In this example, the useEffect hook filters a list of items based on the user's input. The effect runs whenever the filter or items values change, ensuring the filtered list is updated accordingly.

3. Without a Dependency Array

When you use the useEffect hook without providing a dependency array (not an empty array, just no array at all), it means the effect will run after every render, this means when mounting and on every update of the component due to changes in its props or state. This can lead to performance issues and unexpected behavior, especially if you're updating the state within the effect.

I honestly can't think of a good real life example of when to use this, in my almost 3 years of experience working with React I've never used the useEffect hook like this, if you know of a good use case please let me know in the comments!

Conclusion:

Congratulations! You've taken a significant step toward mastering the useEffect hook. Let's recap the key points we covered in this article:

  • If you use an empty dependency array, the code block will only execute once, during component mounting
  • If you pass values to the dependencies array, this will trigger the effect when the component mounts AND when the specific values within the dependency array change.
  • If you use useEffect without a dependency array it will execute the code after every render.

By understanding these three main use cases of useEffect, you now have the power to handle side effects and component lifecycles efficiently. Remember to use this knowledge wisely and adapt it to your projects' needs.

Happy coding, and may your React applications thrive!

Top comments (6)

Collapse
 
brense profile image
Rense Bakker

Good article 👍 I would like to add that it's important to always include all necessary dependencies to the dependency array and not to take any shortcuts, to try make your effect only run on component mount!

Collapse
 
alais29dev profile image
Alfonsina Lizardo

That's correct! thank you very much for your input. I make that mistake sometimes without noticing and Error Lens reminds me of fixing it!

Collapse
 
levischouten profile image
Levi Schouten

Wish I had this guide when I started with react hooks 🔥

Collapse
 
alais29dev profile image
Alfonsina Lizardo • Edited

I wish I had written it sooner then 😅 glad you liked it!

Collapse
 
caropi30 profile image
Carol Pirela - Front End Developer

Amazing post!! It’s nice y to have an easy explanation about Thais particular hook, that in my case always gets me dizzy! Thanks!!

Collapse
 
alais29dev profile image
Alfonsina Lizardo

Awesome! I'm glad it helped! :D