useEffect Hook - Most used hook in React JS

The useEffect hook in React is a powerful tool that allows you to manage side effects within your components. Whether you’re fetching data, updating the DOM, or controlling external systems, useEffect is your go-to solution. In this blog post, we’ll dive deep into how to use it effectively, along with practical examples.

What is the useEffect Hook?

The useEffect hook is part of React’s arsenal of hooks. It enables you to perform side effects (such as data fetching, DOM manipulation, or setting up subscriptions) in functional components. Think of it as a bridge between your component and the outside world.

Basic Usage

Let’s start with the basics. You can use useEffect by calling it at the top level of your component. Here’s the syntax:

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

function MyComponent() {
  const [data, setData] = useState([]);

  useEffect(() => {
    // Your side effect logic goes here
    fetchData().then((result) => {
      setData(result);
    });

    // Cleanup function (optional)
    return () => {
      // Clean up any resources (e.g., subscriptions)
    };
  }, []); // Dependency array (optional)

  // Rest of your component...
}

In this example:

  • We fetch data asynchronously and update the component state.

  • The optional cleanup function runs when the component unmounts.

Examples

Let’s explore some real-world scenarios:

  1. Fetching Data from an API:
useEffect(() => {
  fetch('https://api.example.com/data')
    .then((response) => response.json())
    .then((data) => {
      setData(data);
    });
}, []);
  1. Updating the Document Title:
useEffect(() => {
  document.title = `New Messages: ${unreadCount}`;
}, [unreadCount]);
  1. Subscribing to WebSocket Events:
useEffect(() => {
  const socket = new WebSocket('wss://api.example.com/socket');
  socket.addEventListener('message', handleSocketMessage);

  return () => {
    socket.removeEventListener('message', handleSocketMessage);
    socket.close();
  };
}, []);
  1. Controlling a Non-React Widget (e.g., Google Maps):
useEffect(() => {
  const map = new google.maps.Map(document.getElementById('map'), {
    center: { lat: 40.7128, lng: -74.0060 },
    zoom: 10,
  });

  // Clean up when the component unmounts
  return () => {
    map.setMap(null);
  };
}, []);

// Render the map container
<div id="map" style={{ height: '400px' }}></div>

Let’s delve deeper into the useEffect hook and explore how it differs from useState in React.

Understanding the Basic difference between useState and useEffect

1. useState:

  • The useState hook is primarily used for managing state variables within functional components.

  • It allows you to declare and update state variables directly in your component’s main function body.

  • When you call useState, it returns an array with two elements: the current state value and a function to update that value.

  • Example of using useState:

      import React, { useState } from 'react';
    
      function Counter() {
        const [count, setCount] = useState(0);
    
        return (
          <div>
            <p>Count: {count}</p>
            <button onClick={() => setCount(count + 1)}>Increment</button>
          </div>
        );
      }
    

2. useEffect:

  • The useEffect hook is all about handling side effects in functional components.

  • Side effects include actions like data fetching, DOM manipulation, or setting up subscriptions.

  • You define useEffect separately from your component’s main function body.

  • It runs after the component renders and re-renders.

  • Example of using useEffect:

      import React, { useState, useEffect } from 'react';
    
      function DataFetcher() {
        const [data, setData] = useState([]);
    
        useEffect(() => {
          // Fetch data from an API
          fetchData().then((result) => {
            setData(result);
          });
    
          // Optional cleanup function
          return () => {
            // Clean up any resources (e.g., subscriptions)
          };
        }, []);
    
        return (
          <div>
            {/* Display fetched data */}
          </div>
        );
      }
    

Key Differences

  1. Purpose:

    • useState: Manages state variables.

    • useEffect: Handles side effects.

  2. Usage:

    • useState is used directly within the component’s main function body.

    • useEffect is defined separately and runs after rendering.

  3. State Updates:

    • useState updates are synchronous and trigger immediate re-renders.

    • useEffect does not directly update state but allows you to react to changes (e.g., by fetching data).

  4. Dependency Array:

    • In useEffect, you can specify a dependency array to control when the effect runs.

    • If the dependency array is empty, the effect runs only once (similar to componentDidMount).

Remember these differences, and you’ll be well-equipped to use both hooks effectively in your React applications!