>  기사  >  웹 프론트엔드  >  완전한 redux 툴킷(파트 - 4)

완전한 redux 툴킷(파트 - 4)

PHPz
PHPz원래의
2024-09-11 14:32:39895검색

Complete redux toolkit (Part - 4)

4부: RTK 쿼리의 고급 주제.

이 부분에서는 쿼리 사용자 정의, 인증 처리, 낙관적 업데이트, 성능 최적화를 포함하여 RTK 쿼리의 고급 기능과 사용 사례에 중점을 둘 것입니다.

파트 4: RTK 쿼리의 고급 주제

1. 고급 RTK 쿼리 개념 소개

이전 부분에서는 RTK 쿼리를 사용하여 데이터를 가져오고 변형하는 기본 사항을 다루었습니다. 이제 RTK 쿼리를 더욱 강력하게 만드는 고급 기능을 자세히 살펴보겠습니다. 이러한 기능을 사용하면 쿼리를 사용자 정의하고, 인증을 관리하고, 성능을 최적화하고, 보다 원활한 사용자 경험을 위한 낙관적 업데이트를 처리할 수 있습니다.

2. 인증을 위한 baseQuery 사용자 정의

인증이 필요한 API로 작업할 때는 JWT 토큰이나 API 키와 같은 인증 헤더를 포함하도록 baseQuery를 사용자 정의해야 합니다.

1단계: 사용자 정의 baseQuery 생성

모든 요청에 ​​인증 헤더를 추가하는 사용자 정의 baseQuery 함수를 생성할 수 있습니다.

// src/app/customBaseQuery.js
import { fetchBaseQuery } from '@reduxjs/toolkit/query/react';

const customBaseQuery = fetchBaseQuery({
  baseUrl: 'https://jsonplaceholder.typicode.com/',
  prepareHeaders: (headers, { getState }) => {
    const token = getState().auth.token; // Assuming auth slice has token
    if (token) {
      headers.set('Authorization', `Bearer ${token}`);
    }
    return headers;
  },
});

export default customBaseQuery;

설명:

  • prepareHeaders: 이 기능을 사용하면 각 요청에 대한 헤더를 사용자 정의할 수 있습니다. Redux 저장소에서 토큰을 검색하여 Authorization 헤더에 연결합니다.

2단계: createApi에서 사용자 지정 baseQuery 사용

맞춤형 baseQuery를 사용하도록 postApi.js 파일을 수정하세요.

// src/features/posts/postsApi.js
import { createApi } from '@reduxjs/toolkit/query/react';
import customBaseQuery from '../../app/customBaseQuery';

export const postsApi = createApi({
  reducerPath: 'postsApi',
  baseQuery: customBaseQuery, // Use the custom base query here
  tagTypes: ['Post'],
  endpoints: (builder) => ({
    fetchPosts: builder.query({
      query: () => 'posts',
      providesTags: (result) =>
        result ? result.map(({ id }) => ({ type: 'Post', id })) : ['Post'],
    }),
    addPost: builder.mutation({
      query: (newPost) => ({
        url: 'posts',
        method: 'POST',
        body: newPost,
      }),
      invalidatesTags: ['Post'],
    }),
  }),
});

export const { useFetchPostsQuery, useAddPostMutation } = postsApi;

3. RTK 쿼리를 통한 낙관적 업데이트

낙관적 업데이트를 사용하면 서버가 변형을 확인하기 전에 즉시 UI를 업데이트하여 보다 원활한 사용자 경험을 제공할 수 있습니다. 서버에서 오류가 반환되면 UI가 이전 상태로 되돌아갈 수 있습니다.

1단계: 돌연변이에서 낙관적 업데이트 구현

RTK 쿼리에서 제공하는 onQueryStarted 수명 주기 메서드를 사용하여 낙관적 업데이트를 구현할 수 있습니다.

// src/features/posts/postsApi.js
addPost: builder.mutation({
  query: (newPost) => ({
    url: 'posts',
    method: 'POST',
    body: newPost,
  }),
  invalidatesTags: ['Post'],
  onQueryStarted: async (newPost, { dispatch, queryFulfilled }) => {
    // Optimistic update: immediately add the new post to the cache
    const patchResult = dispatch(
      postsApi.util.updateQueryData('fetchPosts', undefined, (draftPosts) => {
        draftPosts.push({ id: Date.now(), ...newPost }); // Fake ID for optimistic update
      })
    );
    try {
      await queryFulfilled; // Await server response
    } catch {
      patchResult.undo(); // Revert if the mutation fails
    }
  },
}),

설명:

  • onQueryStarted: 이 수명 주기 메서드는 변형이 시작될 때 트리거됩니다. 캐시 업데이트를 관리하기 위해 디스패치 및 queryFulfilled 매개변수를 제공합니다.
  • postApi.util.updateQueryData: 이 유틸리티 기능을 사용하면 캐시된 데이터를 낙관적으로 업데이트할 수 있습니다.
  • patchResult.undo(): 서버가 오류를 반환하는 경우 낙관적 업데이트를 되돌립니다.

4. 종속 쿼리 처리

때때로 하나의 쿼리가 다른 쿼리의 결과에 종속되는 종속 쿼리를 수행해야 할 수도 있습니다. RTK 쿼리는 쿼리 실행 시기를 제어하기 위한 건너뛰기 매개변수를 제공합니다.

예: 선택한 게시물 ID를 기반으로 게시물 세부 정보 가져오기

// src/features/posts/PostDetails.js
import React from 'react';
import { useFetchPostQuery } from './postsApi';

const PostDetails = ({ postId }) => {
  const { data: post, error, isLoading } = useFetchPostQuery(postId, { skip: !postId });

  if (!postId) return <p>Select a post to view details.</p>;
  if (isLoading) return <p>Loading...</p>;
  if (error) return <p>Error loading post details.</p>;

  return (
    <div>
      <h3>{post.title}</h3>
      <p>{post.body}</p>
    </div>
  );
};

export default PostDetails;

설명:

  • useFetchPostQuery: postId를 인수로 사용하는 쿼리 후크입니다. postId가 제공되지 않으면 {skip: !postId }를 사용하여 쿼리를 건너뜁니다.

5. RTK 쿼리를 통한 폴링 및 실시간 데이터

RTK 쿼리는 지정된 간격으로 데이터를 최신 상태로 유지하기 위해 폴링을 지원합니다. 실시간 데이터 동기화에 유용합니다.

1단계: 쿼리에 폴링 사용

pollingInterval 옵션을 사용하면 모든 쿼리에 대해 폴링을 활성화할 수 있습니다.

// src/features/posts/PostsList.js
import React from 'react';
import { useFetchPostsQuery } from './postsApi';

const PostsList = () => {
  const { data: posts, error, isLoading } = useFetchPostsQuery(undefined, {
    pollingInterval: 30000, // Poll every 30 seconds
  });

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

  return (
    <section>
      <h2>Posts</h2>
      <ul>
        {posts.map((post) => (
          <li key={post.id}>{post.title}</li>
        ))}
      </ul>
    </section>
  );
};

export default PostsList;

설명:

  • pollingInterval: 이 옵션은 쿼리가 새 데이터에 대해 서버를 폴링해야 하는 간격(밀리초)을 지정합니다.

6. selectFromResult를 사용하여 성능 최적화

RTK 쿼리는 쿼리 결과에서 특정 데이터를 선택할 수 있도록 하여 고급 성능 최적화를 위한 selectFromResult 옵션을 제공합니다.

1단계: selectFromResult를 사용하여 재렌더링 최적화

selectFromResult 옵션을 사용하면 쿼리 결과의 하위 집합만 필요한 경우 불필요한 다시 렌더링을 방지할 수 있습니다.

// src/features/posts/PostTitleList.js
import React from 'react';
import { useFetchPostsQuery } from './postsApi';

const PostTitleList = () => {
  const { data: posts } = useFetchPostsQuery(undefined, {
    selectFromResult: ({ data }) => ({ titles: data?.map((post) => post.title) }),
  });

  return (
    <section>
      <h2>Post Titles</h2>
      <ul>
        {posts?.map((title, index) => (
          <li key={index}>{title}</li>
        ))}
      </ul>
    </section>
  );
};

export default PostTitleList;

설명:

  • selectFromResult: 이 옵션을 사용하면 가져온 게시물에서 제목만 선택할 수 있어 쿼리 결과의 다른 데이터가 변경될 때 불필요하게 다시 렌더링되는 것을 방지할 수 있습니다.

7. 결론 및 다음 단계

이 부분에서는 인증을 위한 baseQuery 사용자 정의, 낙관적 업데이트 처리, 종속 쿼리 관리, 실시간 데이터 동기화를 위한 폴링 사용, selectFromResult를 통한 성능 최적화 등 RTK 쿼리의 고급 주제를 살펴보았습니다. RTK 쿼리의 풍부한 기능 세트는 최신 Redux 애플리케이션에서 데이터 가져오기 및 캐싱을 처리하기 위한 강력한 도구입니다.

다음 부분에서는 Redux 툴킷 및 RTK 쿼리에 대한 테스트 전략에 대해 논의하고, 강력하고 유지 관리 가능한 코드를 보장하기 위한 단위 테스트, 통합 테스트 및 모범 사례를 다룹니다.

파트 5: Redux 툴킷 및 RTK 쿼리에 대한 테스트 전략을 계속 지켜봐 주시기 바랍니다!

위 내용은 완전한 redux 툴킷(파트 - 4)의 상세 내용입니다. 자세한 내용은 PHP 중국어 웹사이트의 기타 관련 기사를 참조하세요!

성명:
본 글의 내용은 네티즌들의 자발적인 기여로 작성되었으며, 저작권은 원저작자에게 있습니다. 본 사이트는 이에 상응하는 법적 책임을 지지 않습니다. 표절이나 침해가 의심되는 콘텐츠를 발견한 경우 admin@php.cn으로 문의하세요.