
This post is based on information on customer hooks and data fetching provided by others such as Robin Wieruch (https://www.robinwieruch.de/) and Kent Dodds (https://kentcdodds.com/blog/how-to-optimize-your-context-value).
This is a customer hook to fetch energy market data from the Australian Energy Market Operator (AEMO) website (http://data.wa.aemo.com.au/datafiles/balancing-summary/) . In this case Balance Market Summary data for 2019.
First, the following code is the custom hook. This hook:
- uses state to
- store the fetched data, and enable it to be set ([data, setData]);
- store the url from where the data should be fetched, and enable it to be set ([url, setUrl]);
- store a refresh state and allow it to be set, in order to trigger a refresh of the last fetched url data ([refresh, setRefresh]); and
- store a loading state and allow it to be set([isLoading, setIsLoading]);
- uses an effect to
- perform the initial fetch and set the data in the data state;
- manage setting and removing of the loading state; and
- refetching the data (refresh) or fetching the data from a new url (url) if either of those states change.
- has two helper functions
- doRefresh, which forces a refetch of the last url loaded; and
- doFetch, which forces a fetch from a new, passed-in, url.
The data, isLoading state, and helper functions doRefresh and doFetch, are exported as named exports and the overall hook useAemoData is exported as the default export.
// custom hook to handle fetching AEMO data from the ARMO website. import { useState, useEffect } from 'react'; import axios from 'axios'; const useAemoData = () => { // AEMO data to be passeded into the app const [data, setData] = useState(null); // url to fetch. const [url, setUrl] = useState( 'http://data.wa.aemo.com.au/datafiles/balancing-summary/balancing-summary-2019.csv' ); // toggle to refresh the AEMO data const [refresh, setRefresh] = useState(0) // loading data state const [isLoading, setIsLoading] = useState(false); // useEffect to do an initial fetch on component mount and then // every time either the url changes or a refresh is requested. useEffect(() => { const fetchData = async () => { setIsLoading(true); try { const result = await axios(url); setData(result.data); } catch (err) { console.log(err); } setIsLoading(false) }; fetchData(); }, [url, refresh]); // refresh function which will refresh the last requested (or default) url const doRefresh = () => { setRefresh(refresh => refresh + 1); } // do a fetch with a passed in url const doFetch = (url) => { setUrl(url); } return { data, isLoading, doRefresh, doFetch }; } export default useAemoData;
A simple way to use the hook is, for example, in a simple App.js component such as that below.
import React from 'react'; ... ... import useAemoData from './hooks/useAemoData'; const App = () => { let { data, isLoading, doRefresh } = useAemoData(); return ( {isLoading ? <p> Loading ... </p> : {data} } )
Recent Comments