UseFetch Hook

The useFetch hook is a custom hook in React that allows you to easily make HTTP requests and handle responses using the fetch API. It's a convenient way to fetch data in your React components without the need to manually handle the Promise returned by the fetch call.

Basic Example

import { useState, useEffect } from 'react';

export function useFetch(url, options) {
  const [data, setData] = useState(null);
  const [loading, setLoading] = useState(true);
  const [error, setError] = useState(null);

  useEffect(() => {
    async function fetchData() {
      try {
        const res = await fetch(url, options);
        const json = await res.json();
        setData(json);
        setLoading(false);
      } catch (err) {
        setError(err);
        setLoading(false);
      }
    }

    fetchData();
  }, [url, options]);

  return { data, loading, error };
}

For example:

function MyComponent() {
  const { data, loading, error } = useFetch('https://my-json-api.com/posts');

  if (loading) {
    return <p>Loading...</p>;
  }

  if (error) {
    return <p>An error occurred: {error.message}</p>;
  }

  return (
    <ul>
      {data.map(post => (
        <li key={post.id}>{post.title}</li>
      ))}
    </ul>
  );
}

Making Different HTTP Requests

By default, the useFetch hook makes a GET request to the provided URL. However, you can make other HTTP requests by passing an options object as the second argument to the hook.

For example, to make a POST request, you can pass an options object with the method property set to 'POST':

const { data, loading, error } = useFetch(
  'https://my-json-api.com/posts',
  {
    method: 'POST',
    body: JSON.stringify({ title: 'My new post' }),
    headers: {
      'Content-Type': 'application/json'
    }
  }
);

You can also make PUT, PATCH, and DELETE requests in a similar way by setting the method property to the appropriate method.

Adding Query Parameters

To add query parameters to your request, you can use the URLSearchParams API to build a query string and append it to the URL.

const params = new URLSearchParams();
params.append('sort', 'votes');
params.append('limit', '10');

const { data, loading, error } = useFetch(
  `https://my-json-api.com/posts?${params.toString()}`
);

Handling HTTP Headers

You can set HTTP headers in the useFetch hook by passing an options object with a headers property. The headers property should be an instance of the Headers class or an object with keys and values representing the headers.

Here's an example of how to set the Content-Type header in a POST request:

const { data, loading, error } = useFetch(
  'https://my-json-api.com/posts',
  {
    method: 'POST',
    body: JSON.stringify({ title: 'My new post' }),
    headers: {
      'Content-Type': 'application/json'
    }
  }
);

You can also set multiple headers by adding more key-value pairs to the headers object.

Handling HTTP Errors

If the HTTP request fails, the useFetch hook will return an error object with information about the failure. You can handle HTTP errors in your component by checking for the existence of the error object and displaying an error message to the user.

For Example:

if (error) {
  return <p>An error occurred: {error.message}</p>;
}

Adding Custom Logic

In addition to the basic functionality provided by the useFetch hook, you can also add your own custom logic to the hook. For example, you might want to add a debouncing or throttling effect to your requests to prevent overloading the server with too many requests.

To add custom logic to the useFetch hook, you can define your own hook that calls the useFetch hook and adds your custom logic. Here's an example of how to define a custom hook that debounces the useFetch hook:

import { useFetch, useState, useEffect } from 'react';

function useDebouncedFetch(url, options, delay) {
  const [debouncedUrl, setDebouncedUrl] = useState(url);
  const [debouncedOptions, setDebouncedOptions] = useState(options);
  const { data, loading, error } = useFetch(debouncedUrl, debouncedOptions);

  useEffect(() => {
    const timer = setTimeout(() => {
      setDebouncedUrl(url);
      setDebouncedOptions(options);
    }, delay);

    return () => clearTimeout(timer);
  }, [url, options, delay]);

  return { data, loading, error };
}

You can then use the custom useDebouncedFetch hook in your component just like the useFetch hook:

const { data, loading, error } = useDebouncedFetch(
  'https://my-json-api.com/posts',
  { method: 'POST' },
  1000
);

Summary

The useFetch hook is a convenient way to fetch data in your React components without the need to manually handle the Promise returned by the fetch call. It allows you to make different HTTP requests, add query parameters and headers, and handle HTTP errors. You can also add custom logic to the hook to customize its behavior.

Did you find this article valuable?

Support Divij Sehgal by becoming a sponsor. Any amount is appreciated!