1componentWillUnmount() {
2 // fix Warning: Can't perform a React state update on an unmounted component
3 this.setState = (state,callback)=>{
4 return;
5 };
6}
7
1useEffect(() => {
2 let isMounted = true; // note mutable flag
3 someAsyncOperation().then(data => {
4 if (isMounted) setState(data); // add conditional check
5 })
6 return () => { isMounted = false }; // cleanup toggles value, if unmounted
7}, []); // adjust dependencies to your needs
8
1// custom Hook for automatic abortion on unmount or dependency change
2// You might add onFailure for promise errors as well.
3function useAsync(asyncFn, onSuccess) {
4 useEffect(() => {
5 let isActive = true;
6 asyncFn().then(data => {
7 if (isActive) onSuccess(data)
8 else console.log("aborted setState on unmounted component")
9 });
10 return () => {
11 isActive = false;
12 };
13 }, [asyncFn, onSuccess]);
14}
15
16const Child = () => {
17 const [state, setState] = useState("loading (4 sec)...");
18 useAsync(simulateFetchData, setState);
19 return <div>Child: {state}</div>;
20};
21
22const Parent = () => {
23 const [mounted, setMounted] = useState(true);
24 return (
25 <div>
26 Parent:
27 <button onClick={() => setMounted(!mounted)}>
28 {mounted ? "Unmount" : "Mount"} Child
29 </button>
30 {mounted && <Child />}
31 <p>
32 Unmount Child, while it is still loading. It won't set state later on,
33 so no error is triggered.
34 </p>
35 </div>
36 );
37};
38
39const simulateFetchData = () => new Promise(
40 resolve => setTimeout(() => resolve("data fetched"), 4000));
41
42ReactDOM.render(<Parent />, document.getElementById("root"));
1export default function MyComponent() {
2 const [loading, setLoading] = useState(false);
3 const [someData, setSomeData] = useState({});
4 let componentMounted = true; // (3) component is mounted
5 // ...
6 useEffect(() => {
7 setLoading(true);
8 someResponse = await doVeryLongRequest(); // it needs some time
9 // When request is finished:
10 if (componentMounted){ // (5) is component still mounted?
11 setSomeData(someResponse.data); // (1) write data to state
12 setLoading(false); // (2) write some value to state
13 }
14 return () => { // This code runs when component is unmounted
15 componentMounted = false; // (4) set it to false if we leave the page
16 }
17 }, []);
18
19 return (
20 <div className={loading ? "loading" : ""}>
21 {someData}
22 <a href="SOME_LOCAL_LINK">Go away from here!</a>
23 </div>
24 );
25}
26