Skip to content

Instantly share code, notes, and snippets.

@csenio
Created October 28, 2019 14:48
Show Gist options
  • Save csenio/81975a8cfb029177221c53193a141849 to your computer and use it in GitHub Desktop.
Save csenio/81975a8cfb029177221c53193a141849 to your computer and use it in GitHub Desktop.
import {useState, useReducer, useEffect} from 'react'
import axios from 'axios'
import {toastAlert, getError} from '@helpers'
const dataFetchReducer = (state, action) => {
switch (action.type) {
case 'FETCH_INIT':
return {
...state,
isLoading: true,
error: false,
}
case 'FETCH_SUCCESS':
return {
...state,
isFetched: true,
isLoading: false,
error: false,
data: action.payload,
}
case 'FETCH_FAILURE':
return {
...state,
isFetched: true,
isLoading: false,
error: true,
}
default:
throw new Error()
}
}
const useFetch = (initialUrl, initialData) => {
const [url, setUrl] = useState(initialUrl)
const [state, dispatch] = useReducer(dataFetchReducer, {
isFetched: false,
isLoading: false,
error: false,
data: initialData,
})
useEffect(() => {
let didCancel = false
const fetchData = async () => {
dispatch({type: 'FETCH_INIT'})
try {
const result = await axios(url)
if (!didCancel) {
dispatch({type: 'FETCH_SUCCESS', payload: result.data})
}
} catch (error) {
if (!didCancel) {
toastAlert('error', getError(error))
dispatch({type: 'FETCH_FAILURE'})
}
}
}
fetchData()
return () => {
didCancel = true
}
}, [url])
return [state, setUrl]
}
export default useFetch
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment