React-Query - #3 core concepts

YEZI🎐·2022년 11월 8일
0

React

목록 보기
25/29

React-Query

React-Query는 fetching, caching, synchronizing, and updating server state 등을 쉽게 만들어 주는 React 라이브러리이다.

3 core concepts

  • Queries
  • Mutations
  • Query Invalidation

Queries

  • Queries는 서버에서 데이터를 패칭하기 위한 Promise 기반 메서드(GET 메서드 및 POST 메서드 포함)인 비동기 함수와 사용된다.
  • useQuery() Hook 사용
  • unique key 필요
  • promise를 return 하는 함수 필요
    • Resolves the data, or
    • Throws an error

기본 문법

import { useQuery } from '@tanstack/react-query'

function App() {
  const info = useQuery({ queryKey: [**unique key**], queryFn: **비동기 함수** })
  /* ↑ 같은 거 ↓ */
  const info = useQuery({ queryKey: ['todos'], queryFn: fetchTodoList })
}

Returns(반환값)

  • isLoading or status === 'loading' : 아직 데이터 없음
  • isError or status === 'error' : 오류 발생
    (error : 해당 property로 에러 메세지를 확인할 수 있음)
  • isSuccess or status === 'success' : 성공하여 데이터 사용 가능
    (data : 해당 property로 성공한 데이터를 확인할 수 있음)

사용 법

  1. 상위 컴포넌트에 import QueryClientProvider, QueryClient

    import { QueryClientProvider, QueryClient } from 'react-query';-
  2. 새로운 QueryClient 변수를 선언

    const queryClient = new QueryClient();
  3. queryClient 객체를 전역에서 사용할 수 있도록 QueryClientProvider로 감싸줌

    import { QueryClientProvider, QueryClient } from 'react-query';
    
    const queryClient = new QueryClient();
    
    export default function ParentCompnt() {
     return (
       /* 이 부분 */
       <QueryClientProvider client={ queryClient }>
         <BrowserRouter>
           <Routes>
             <Route path="/" element={<Home />} />
             <Route path="/edit" element={<ChildrenCompnt />} />
           </Routes>
         </BrowserRouter>
       </QueryClientProvider>
       /* 이 부분 */
     );
    }
  4. 하위 컴포넌트에 import useQuery

    import { useQuery } from "react-query";
  5. Promise 기반 메서드 import

    import { 메서드명 } from "메서드 경로";
  6. useQuery를 사용하여 unique key 설정

    import { useQuery } from "react-query";
    import { 메서드명 } from "메서드 경로";
    
    export default function ChildrenCompnt() {
     const [inputValue, setInputValue] = useState("");
     
     /* 이 부분 */
     const { data, isLoading } = useQuery('**unique key**', 메서드명)
     /* 이 부분 */
     
     if ( isLoading ) return <span>Loading...</span>
    
     return (
       <>
         <h3>Hello World</h3>
       </>
     );
    }

Mutations

  • Queries와 달리 Mutations는 일반적으로 데이터를 create/update/delete 하거나 서버 부가효과(side effect)를 수행하는데 사용된다.
  • useMutation() Hook 사용
  • mutate를 위한 POST, PUT, DELETE 및 각 요청에 필요한 인자들이 포함된 패치함수 필요
  • 옵션 값

기본 문법

import { useMutation } from "react-query";

function App() {
  const { data, isLoading, mutate } = useMutation(**mutate를 위한 패치함수**, options);
  /* ↑ 같은 거 ↓ */
  const { data, isLoading, mutate } = useMutation(mutationFn, options);
}

Options

  • onMutate: (variables) => { return { id: 1 } };
    mutation 전에 실행되는 함수로, 미리 렌더링 하고자할 때 유용
    이 함수가 반환하는 값을 아래 함수들의 context로 사용 가능
  • onSuccess: (data, variables, context) => {}
    mutation이 성공하고 결과를 전달할 때 실행
  • onError: (error, variables, context) => {}
    mutation이 실패했을 시 에러를 전달
  • onSettled: (data, error, variables, context) => {}
    mutation의 성공/실패 여부와 상관없이 완료됬을 때 실행

Returns(반환값)

  • isIdle or status === 'idle' : 가동되지 않은 상태이거나 새로 고침/재설정된 상태
  • isLoading or status === 'loading' : 실행 중
  • isError or status === 'error' : 오류 발생
    (error : 해당 property로 에러 메세지를 확인할 수 있음)
  • isSuccess or status === 'success' - 성공하여 데이터 사용 가능
    (data : 해당 property로 성공한 데이터를 확인할 수 있음)

사용 법

  1. import useMutation

    import { useMutation } from 'react-query';-
  2. mutate를 위해 필요한 인자들이 포함된 패치함수 import

    import { 패치함수 } from "패치함수 경로";
  3. 새로운 useMutation 변수를 선언

    const mutation = useMutation(**패치함수**);
  4. 변경 값 패치함수로 전달

    import { useMutation } from 'react-query';
    import { 패치함수 } from "패치함수 경로";
    
    export default function ChildrenCompnt() {
    
     const mutation = useMutation(**패치함수**);
    
     /* 이 부분 */
     const handleSubmit = (e) => {
       e.preventDefault();
       mutation.mutate(inputValue)
     };
     /* 이 부분 */
    
     return (
       <>
         <form onSubmit={handleSubmit}>
           <label>
             변경할 닉네임:
             <input type="text" value={inputValue} onChange={handleChange} />
           </label>
         </form>
       </>
     );
    }

Query Invalidation

  • 썩은(stale)쿼리의 폐기(invalidation)
  • 쿼리의 데이터가 요청을 통해 서버에서 바뀌었다면, 백그라운드에 남아있는 데이터는 과거의 것이 되어 앱에서 쓸모없어지는 상황이 발생할 수 있다.
  • invalidateQueries()를 사용하면 개발자가 명시적으로 query가 stale 되는 지점을 찝어줄 수 있다. 해당 메소드가 호출되면 쿼리가 바로 stale 되고, 리패치가 진행된다.
  • 쿼리에 특정 키가 공통적으로 들어가있다면 싸잡아서 Invalidation이 가능하다.
  • useQueryClient() Hook 사용

기본 문법

queryClient.invalidateQueries();
// 캐시가 있는 모든 쿼리들을 invalidate한다.

queryClient.invalidateQueries('todos');
// 'todos'로 시작하는 모든 쿼리들을 invalidate한다.

queryClient.invalidateQueries({
  predicate: (query) => query.queryKey[0] === 'todos' && query.queryKey[1]?.version >= 10,
});

사용 법

  1. import useQueryClient

    import { useQueryClient } from 'react-query';-
  2. 새로운 useQueryClient 변수를 선언

    const queryClient = useQueryClient();
  3. invalidateQueries()를 사용하여 캐시가 있는 모든 쿼리들을 invalidate

    import { useMutation, useQueryClient } from "react-query";
    import { 패치함수 } from "패치함수 경로";
    
    export default function ChildrenCompnt() {
    
     /* 이 부분 */
     const mutation = useMutation(**패치함수**, {
       onSuccess: () => {
         queryClient.invalidateQueries()
       }
     });
     /* 이 부분 */
    
     const handleSubmit = (e) => {
       e.preventDefault();
       mutation.mutate(inputValue)
     };
    
     return (
       <>
         <form onSubmit={handleSubmit}>
           <label>
             변경할 닉네임:
             <input type="text" value={inputValue} onChange={handleChange} />
           </label>
         </form>
       </>
     );
    }


References

profile
까먹지마도토도토잠보🐘

0개의 댓글