Ter maior controle do cache e armazenamento configurável dos resultados das solicitações REST são requisitos fundamentais, principalmente nas aplicações atuais que desejam evitar uma quantidade demasiada de requisições.

O axios-cache-adapter, como o nome mesmo diz, é um adaptador para auxiliar esse controle do cache das requisições. A partir dele, é possível setar o maxAge, tempo máximo para expiração dos dados, no próprio axios.

1 import { setupCache } from 'axios-cache-adapter'
2 import axios from 'axios-cache-adapter'
3
4 const cache = setupCache({
5   maxAge: 15 * 60 * 1000 // 15 minutos para expiração
6 })
7
8 const api = axios.create({
9   adapter: cache.adapter
10 })

No código anterior importamos a função setupCache na linha 1. Esta função, na linha 4, recebe um objeto com a propriedade maxAge para determinar o tempo de expiração dos dados no adaptador. No exemplo acima, os dados expirarão após os 15 minutos. Na linha 8 é possível configurarmos o adaptador no próprio axios, assim as requisições idênticas no intervalo de 15 minutos não serão realizadas no servidor, mas serão consultadas no adaptador.

Opa, uma melhoria considerável é utilizar a função setup para obter uma instância do axios pré-configurado no axios-cache-adapter. Assim, é possível remover o axios como dependência direta em seu projeto:

1 import { setup } from 'axios-cache-adapter'
2
3 const api = setup({
4  baseURL: 'http://some-rest.api',
5  cache: {
6    maxAge: 15 * 60 * 1000  }
7 })

No código anterior importamos a função setup na linha 1 e criamos uma instância do axios pré-configurando o axios-cache-adapter com 15 minutos de cache.

Existe algumas situações que podem vir à sua cabeça a partir dessas informações:

  • Há alguma maneira de configurar o tempo de expiração do cache para uma requisição específica?
  • Como posso garantir que a requisição seja realizada no servidor mesmo sem a expiração das informações em cache?

A configuração global simplifica a configuração da expiração dos dados, mas é possível sobrescrever as configurações de cache para requisições específicas:

api.get('/get?with=query', {
  cache: {
    maxAge: 2 * 60 * 1000
  }
})

Para garantir que a requisição traga dados “fresquinhos” é possível usar o parâmetro cache-control. Este parâmetro com valor no-cache garante que os dados solicitados vieram do servidor, como no código a seguir:

api.get('/get?with=query&cache-control=no-cache')

Local de armazenamento

Por padrão as informações são gravadas em memória, logo se você atualizar a página perderá os dados em cache. Se esse não é o comportamento esperado, temos uma solução com localforage.

Com o localforage é possível fornecer uma instância para axios-cache-adapter que será usada para armazenar os dados no lugar da memória padrão. É bom ressaltar que essa abordagem funcionará apenas no lado do cliente porque o localforage não funciona no Node.js

import localforage from 'localforage'
import memoryDriver from 'localforage-memoryStorageDriver'
import { setup } from 'axios-cache-adapter'

// Configura `localforage` e retorna uma instância do `axios` com `axios-cache-adapter`
async function configure () {
  // Registre o `memoryDriver` customizado para` localforage`
  await localforage.defineDriver(memoryDriver)

  // Cria uma instância do `localforage`
  const store = localforage.createInstance({
    // Lista os drivers usados
    driver: [
      localforage.INDEXEDDB,
      localforage.LOCALSTORAGE,
      memoryDriver._driver
    ],
    // Adiciona prefixo em todas as chaves de armazenamento para evitar conflitos
    name: 'my-cache'
  })


  return setup({
    baseURL: 'http://some-rest.api',
    cache: {
      maxAge: 15 * 60 * 1000,
      store // Adicionar a instância do `localforage` no armazenamento do `axios-cache-adapter`
    }
  })
}

configure().then(async (api) => {
  const response = await api.get('/url')

  if (anotherResponse.request.fromCache) { 
    console.log("O dado proveio do cache")
  }
})

Com todas essas opções de configuração é possível ter controle do cache das requisições e evitar excesso de solicitações desnecessárias.

E você, o que utiliza para tratar as múltiplas requisições no servidor? Coloque nos comentários ou me marque no twitter @marciovsena

Mais detalhes da documentação em https://github.com/RasCarlito/axios-cache-adapter

Interessou-se pelo assunto “Armazenando em Cache as requisições javascripts com axios”? Fique à vontade para contribuir com a discussão nos comentários. Continue acompanhando o blog da Impulso para ler mais conteúdos como esse!