🍌 Cache. React performance with react-query
Tags: javascript, beginners, react, frontend
Published: 2022-03-14 17:19:32

## 🤔 What is react-query?
React cache library
[Official site](https://react-query.tanstack.com/)

## 🤔 What is cache?


![react-query explanation](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/8y7ev4vzhla1ibnx54x4.png)

Imagine you work at home now, and go to kitchen to take a banana. 1 hour later, you will get hungry and go to kitchen again and again and again ...

Just put bananas on your desk, and take it! you don't need to go to kitchen again and again
```
Bananas = data
kitchen = server
your desk = cache
```
(If you put too much bananas on your desk like 1000, you would work so hardly. Be careful)

 ⏬ ok, I'm gonna reveal details ⏬

## 😢 Weakness state management of classical way
Integrating data from server and React app state
(for example Redux "Store")

_it's like banana and note and pen and other all stuffs are on your desk, just chaos_


## 😇 How to solve this problem?
separate state management, then "react-query" manages sever data with cache. 

_it's like you make small box on your desk for banana_

## 👍 Benefits of using react-query

### 1.Optimize number of fetching  
When only banana on your desk goes bad, you should go to kitchen

### 2.Better UX (less loading time)
When you go to kitchen, you can't work. Waste of time

### 3. Less code

⇩classical code
```javascript
export const useClassicalFetch = () => {
  const { tasks, setTasks } = useStateContext()
  const [isLoading, setLoading] = useState(false)
  const [isError, setError] = useState(false)

  useEffect(() => {
    const fetchData = async () => {
      setError(false)
      setLoading(true)
      try {
        const res = await axios('http://hoge.com/api/tasks/')
        setTasks(res.data)
      } catch (error) {
        setError(true)
      }
      setLoading(false)
    }
    fetchData()
  }, [setTasks])

  return { tasks, isLoading, isError }
}
```

⇩react-query
```javascript
const getTasks = async () => {
  const { data } = await axios.get<Task[]>('http://hoge.com/api/tasks/')
  return data
}

// *** Here definition of react-query ***
export const useQueryTasks = () => {
  return useQuery<Task[], Error>({
    queryKey: 'tasks',
    queryFn: getTasks,
    cacheTime: 10000,//10sec
    staleTime: 10000,
  })
}
```
The way how to use it in component
```javascript
const TaskList: VFC = () => {
  const { status, data } = useQueryTasks()
  if (status === 'loading') return <div>{'Loading...'}</div>
  if (status === 'error') return <div>{'Error'}</div>
  return (
    <div>
      {data?.map((task) => (
        // omit here
      ))}
    </div>
  )
}

```

### 🌟 explanation of react-query configuration values
> staleTime


![staleTime](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/nohjdlyfodgdhvpf5h8d.png)

For example setting 10000ms(10sec).
First 10 seconds after mounting component, cache data is "fresh", after that changes to "stale(old)".

```
fresh -> using cache
stale -> fetch data from server
```
> cacheTime


![cacheTime](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/lkwu839bkug27abqnlaf.png)

For example setting 10000ms(10sec).
After 10 seconds unmounting component, cache data is deleted

> refetchOnWindowFocus

When cursor is focus on windows, fetch data automatically.
```txt
// ex. When you use chrome and firefox. 
use chrome
↓
use firefox
↓
use chrome, then fetch data automatically !
```