React Custom Hooks

Building our own custom Hooks in React allows us to extract logic into reusable functions. This paradigm also improves code legibility in our components by seperating our code into distinct and related functions.

A custom Hook is a JavaScript function whose name starts with ”use”. We can decide what it takes as arguments, and what, if anything, it should return.

To see Hooks in action, let's create a reusable custom Hook to help us with http fetch requests.

Edit usefetch-Hook


Building a custom Hook

Custom Hooks' names must start with use. For our fetch Hook, useFetch makes sense. Custom Hooks are javascript functions that can use other Hooks inside. For our usefetch Hook we can manage the error, loading, and response state by using useState. And we can use useEffect to run the native fetch request.

Custom Hooks can take arguments, and we can optionally return anything. For our useFetch Hook, we'll return an object with the error, loading, and response state. And we'll pass a parameter with the endpoint.

import { useState, useEffect } from 'react'; const useFetch = url => { const [error, setError] = useState(false); const [loading, setLoading] = useState(false); const [response, setResponse] = useState(null); useEffect(() => { const fetchData = async () => { setLoading(true); try { const res = await fetch(url); const data = await res.json(); setResponse(data); } catch (err) { setError(err); } setLoading(false); }; fetchData(); }, [url]); return { error, loading, response }; }; export default useFetch;

Using the custom Hook

Hooks must be used at the top level of our React components, before any early returns. By following this rule we ensure that Hooks are called in the same order each time a component renders.

When using our custom Hook, we pass the endpoint as an argument and we deconstruct the return object to access the error, loading, and response data.

import React from 'react'; import useFetch from './useFetch'; const url = 'https://jsonplaceholder.typicode.com/albums'; const App = () => { const { error, loading, response } = useFetch(url); if (error) { return <div>Something went wrong</div>; } return ( <> {loading ? ( <div>Loading...</div> ) : ( <ul> {response?.length > 0 ? ( response.map(item => ( <li key={item.id}>{item.title}</li> )) ) : ( <li>Empty state</li> )} </ul> )} </> ); }; export default App;

Edit usefetch-Hook


Resource list of React custom Hooks

Custom Hooks cover a wide range of use cases like form handling, animation, declarative subscriptions, timers, etc. The list below offers a very useful list of ready to use custom Hooks.