
Criando um simples hook de fetch com axios
Este pequeno tutorial tem por finalidade mostrar como podemos criar um simples hook para realizar chamadas a API. Durante o desenvolvimento de uma aplicação para estudo, identifiquei que poderia abstrair essa lógica de chamada a API além de adicionar um loading e realizar capturas de quaisquer erros que tenham ocorrido durante o envio da requisição. Será utilizada a API do github.
Pré-requisitos
Como se trata de um pequeno tutorial, assumo que:
- Já tenha uma aplicação react criada;
- Tenha o axios instalado em sua aplicação. Se não estiver, pode instalar com o comando abaixo;
yarn add axiosCriando hook useAxios
1// src/hooks/useAxios.ts
2
3import axios, { AxiosRequestConfig } from 'axios'
4import { useEffect, useState } from "react";
5
6type UseAxiosParams = {
7 url: string
8 // Podemos acrescentar mais métodos de acordo com a necessidade
9 method: 'get' | 'post' | 'put' | 'delete'
10 config?: AxiosRequestConfig | undefined
11 initialValue?: any
12}
13
14const http = axios.create({
15 baseURL: 'https://api.github.com'
16})
17
18export function useAxios<T>({
19 url,
20 method,
21 config = undefined,
22 initialValue
23}: UseAxiosParams) {
24 const [data, setData] = useState<T>(initialValue)
25 const [error, setError] = useState('')
26 const [loading, setLoading] = useState(false)
27
28 useEffect(() => {
29 (async () => {
30 try {
31 switch (method) {
32 case 'get':
33 setLoading(true)
34 const response = await http.get(url, config)
35 if (response.status === 200) {
36 setData(response.data)
37 }
38 break;
39
40 // outros métodos
41 default:
42 break;
43 }
44 } catch (error) {
45 setError(error.message)
46 } finally {
47 setLoading(false)
48 }
49
50 })()
51 }, [url, method])
52
53 return { data, loading, error }
54}
55Temos apenas um exemplo com o método get dentro do switch.
Utilizando o hook
Este arquivo tem o intuito de mostrar como podemos utilizar o hook criado. Desconsidere as tags HTML utilizada no retorno da página Repository.
1// src/pages/Repository/index.tsx
2
3import { useAxios } from '../../hooks/useAxios';
4
5interface Repository {
6 full_name: string;
7 description: string;
8 stargazers_count: number;
9 forks_count: number;
10 open_issues_count: number;
11 owner: {
12 login: string;
13 avatar_url: string;
14 }
15}
16
17const Repository: React.FC = () => {
18 const { data, loading } = useAxios<Repository>({
19 url: `repos/facebook/react`,
20 method: 'get'
21 })
22
23 return (
24 <>
25 {respositoryLoading && <h1>Carregando...</h1>}
26 {repository && (
27 <RepositoryInfo>
28 <header>
29 <img src={repository.owner.avatar_url} alt="git" />
30 <div>
31 <strong>{repository.full_name}</strong>
32 <p>{repository.description}</p>
33 </div>
34 </header>
35 <ul>
36 <li>
37 <strong>{repository.stargazers_count}</strong>
38 <span>Stars</span>
39 </li>
40 <li>
41 <strong>{repository.forks_count}</strong>
42 <span>Forks</span>
43 </li>
44 <li>
45 <strong>{repository.open_issues_count}</strong>
46 <span>Issues abertas</span>
47 </li>
48 </ul>
49 </RepositoryInfo>
50 )}
51 </>
52 );
53}
54
55export default Repository;
56