When Not to Use useEffect

⭐ Interview Importance: MEDIUM
⏱️ Revision Time: 2 min

When Not to Use useEffect

useEffect is a powerful tool, but it is frequently overused. Overusing Effects can lead to slower apps, confusing code, and race conditions.

You do not need useEffect in these two common scenarios:

1. You don’t need Effects to transform data for rendering

If you want to filter a list, calculate a total, or format a string based on props or state, you should not use useEffect to store the result in another state variable.

❌ BAD: Using an Effect to calculate derived state

function Cart({ items }) {
  const [total, setTotal] = useState(0);

  useEffect(() => {
    // This causes an unnecessary extra render!
    const newTotal = items.reduce((sum, item) => sum + item.price, 0);
    setTotal(newTotal);
  }, [items]);

  return <div>Total: {total}</div>;
}

✅ GOOD: Calculate it during rendering

function Cart({ items }) {
  // Calculated during the render. Fast and simple.
  const total = items.reduce((sum, item) => sum + item.price, 0);
  
  return <div>Total: {total}</div>;
}

If the calculation is genuinely slow, wrap it in useMemo instead of useEffect.

2. You don’t need Effects to handle user events

If some code should run because the user did something (like clicking a button, submitting a form, or typing in an input), that code belongs in an event handler, not an Effect.

❌ BAD: Using an Effect for an event

function ProductPage({ product }) {
  const [isBuying, setIsBuying] = useState(false);

  useEffect(() => {
    if (isBuying) {
      // It's hard to track WHY this was triggered.
      post('/api/buy', { id: product.id });
      setIsBuying(false);
    }
  }, [isBuying, product.id]);

  function handleBuyClick() {
    setIsBuying(true); // Triggers the effect indirectly
  }
}

✅ GOOD: Put the logic in the event handler

function ProductPage({ product }) {
  function handleBuyClick() {
    // Direct, easy to read, and exactly where the interaction happens
    post('/api/buy', { id: product.id });
    showNotification('Purchased!');
  }
}

When DO you need an Effect?

You need an Effect when your component must synchronize with an external system because it is displayed on the screen.

Examples:

  • Connecting to a WebSocket when a chat room opens.
  • Fetching data when a specific page loads (though modern routers often handle this outside of React).
  • Attaching a global window event listener (like tracking mouse position).
  • Fading in an element using a third-party animation library like GSAP.

Interview Questions

Q: Is it a good idea to use useEffect to format data received from props before storing it in state?
A: No, this is an anti-pattern. Transforming data for display should be done synchronously during the render phase as a standard variable. Using useEffect causes a completely unnecessary second render cycle (Render -> Commit -> Effect Runs -> Set State -> Render Again).