Created
January 10, 2024 22:59
-
-
Save signalwerk/e020bd8b605ddc380a28606bd9be887d to your computer and use it in GitHub Desktop.
Fetch a JSON and have the option to chancel the request
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import { useState, useEffect } from "react"; | |
const useFetch = (url, options) => { | |
const [response, setResponse] = useState(null); | |
const [error, setError] = useState(null); | |
const [loading, setLoading] = useState(false); | |
const abortController = new AbortController(); // Move abortController outside useEffect | |
useEffect(() => { | |
const signal = abortController.signal; | |
const doFetch = async () => { | |
setLoading(true); | |
try { | |
const res = await fetch(url, { ...options, signal }); | |
const json = await res.json(); | |
if (!signal.aborted) { | |
setResponse(json); | |
} | |
} catch (e) { | |
if (!signal.aborted) { | |
setError(e); | |
} | |
} finally { | |
if (!signal.aborted) { | |
setLoading(false); | |
} | |
} | |
}; | |
doFetch(); | |
return () => { | |
abortController.abort(); | |
}; | |
}, [url, options]); | |
return { response, error, loading, abortController }; // Return abortController here | |
}; | |
export default useFetch; | |
/* | |
import React from "react"; | |
import useFetch from "./useFetch"; | |
const MyComponent = () => { | |
const { response, error, loading, abortController } = useFetch( | |
"https://api.example.com/data", | |
{} | |
); | |
const handleCancel = () => { | |
abortController.abort(); // Call abort method when the button is clicked | |
}; | |
return ( | |
<div> | |
{loading && ( | |
<> | |
<div>Loading...</div> | |
<button onClick={handleCancel}>Cancel Request</button>{" "} | |
</> | |
)} | |
{error && <div>Error: {error.message}</div>} | |
{response && ( | |
<div> | |
<h1>Data Fetched</h1> | |
<pre>{JSON.stringify(response, null, 2)}</pre> | |
</div> | |
)} | |
</div> | |
); | |
}; | |
export default MyComponent; | |
*/ |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment