0

I am having this warning in my console whenever I try to run this custom hook I made for fetching data, here is how it looks like:

import { useState, useEffect } from "react";
import axios from "axios";
const useFetch = (url) => {
  const [data, setData] = useState(null);
  const [error, setError] = useState(null);

  useEffect(() => {
    axios
      .get(url)
      .then((response) => {
        setData(response.data);
      })
      .catch((err) => {
        setError(err);
      });
  }, [url]);

  return { data, error };
};

export default useFetch;

And this is the full warning message:

Warning: Can't perform a React state update on an unmounted component. This is a no-op, but it indicates a memory leak in your application. To fix, cancel all subscriptions and asynchronous tasks in a useEffect cleanup function.

Does anyone know how to fix this?

ahmedskulj10
  • 381
  • 1
  • 15
  • 1
    this issue is addressed here [link](https://stackoverflow.com/questions/53949393/cant-perform-a-react-state-update-on-an-unmounted-component) scroll down to React Hooks specific solution for – Dev-2019 Oct 10 '21 at 17:21

1 Answers1

1

You need to make sure the component is still mounted before trying to update the state:

    import { useState, useEffect } from "react";
import axios from "axios";

const useFetch = (url) => {
      const [data, setData] = useState(null);
      const [error, setError] = useState(null);
      const isMounted=useRef(null)
      useEffect(()=>{ isMounted.current=true; return()=>{isMounted.current=false}},[])
      useEffect(() => {
        axios
          .get(url)
          .then((response) => {
            if (isMounted.current)
            {setData(response.data);}
          })
          .catch((err) => {
            if (isMounted.current)
            {setError(err);}
          });
      }, [url]);
    
      return { data, error };
    };
    
    export default useFetch;

Set a mutable value to true right after the component mounts, and set it to false when it is going to unmount.

Before every setState check if it is still mounted.

Erfan
  • 1,725
  • 1
  • 4
  • 12
  • I did something similiar to this, based on the comment above, and it is working, but thank you for your solution anyways! – ahmedskulj10 Oct 10 '21 at 17:26