跳至主要内容

React Query

React Query 是一個很實用的 React 工具庫,專門用來處理後端資料的獲取、快取、同步和共享。它讓我們在開發資料驅動的應用程式時,可以更輕鬆地與伺服器進行溝通。React Query 能幫助你更有效率地管理應用程式中的資料,無論是從 API 獲取資料、管理資料的加載狀態,還是處理錯誤,都變得更加容易。

React Query 的核心概念

  1. Query:用來取得資料。每個 Query 都會有一個獨特的 key,這個 key 是用來識別和快取資料的。舉例來說,你可以使用 useQuery 這個 hook 來發送 API 請求並取得資料。
  2. Mutation:用來修改資料。當你需要發送 POST、PUT、DELETE 等請求時,可以使用 useMutation 來處理。Mutation 通常適合在表單提交的情境下使用。
  3. Query Client:負責管理和存儲 Query 狀態的實體。透過這個實體,你可以設定全域配置、手動觸發資料重新獲取、清除快取等等。
  4. Cache(快取):React Query 會自動管理資料的快取,你可以設定快取時間,以及是否需要重新獲取快取中的資料。
  5. 背景同步:React Query 支援在背景中自動同步資料,這樣一來,當資料發生變化時,應用程式就會自動更新顯示。

Query

Query 是 React Query 中用來取得資料的核心概念。你可以使用 useQuery 這個 hook 來發送 API 請求並取得資料。 主要的參數有:

  • queryKey:用來識別和快取資料的 key。當 queryKey 發生變化時,React Query 會重新發送 API 請求。
  • queryFn:用來發送 API 請求的函數。

Query 狀態

在 Query 中,狀態可以分成兩大類分別是 statusfetchStatus

  • status:用來表示資料的獲取狀態,有以下幾種值:

    • isPendingstatus === 'pending' - 尚無資料
    • isSuccessstatus === 'success' - 查詢成功
    • isErrorstatus === 'error' - 查詢失敗
  • fetchStatus:用來表示**queryFn 的執行狀態**,有多種情況會觸發,例如:第一次獲取資料、重新獲取資料 (refetch)、對快取資料進行背景更新 (stale-while-revalidate)、手動觸發重新獲取資料等, fetchStatus 有以下幾種值:

    • isIdlefetchStatus === 'idle' - 尚無發送請求
    • isFetchingfetchStatus === 'fetching' - 正在發送請求
    • isPausedfetchStatus === 'paused' - 請求暫停
範例
function Todos() {
const {
status,
data: todos,
error,
isFetching,
} = useQuery({
queryKey: ['todos'],
queryFn: fetchTodos,
});

if (status === 'pending') {
return <span>Loading...</span>;
}

if (status === 'error') {
return <span>Error: {error.message}</span>;
}

return (

<>
{isFetching && <div>Refreshing...</div>}

<div>
{todos.map((todo) => (
<Todo key={todo.id} todo={todo} />
))}
</div>
</>

);
}

Mutation

Mutation 是 React Query 中用來修改資料的核心概念。當你需要發送 POST、PUT、DELETE 等請求時,可以使用 useMutation 來處理。 主要的參數有:

  • mutationFn:用來發送 API 請求的函數。

Mutation 狀態

Mutation 有以下幾種狀態:

  • isIdlestatus === 'idle' - mutation 當前處於空閒狀態或處於全新/重置狀態
  • isPendingstatus === 'pending' - mutation 正在運行
  • isErrorstatus === 'error' - mutation 遇到錯誤
  • isSuccessstatus === 'success' - mutation 成功

Mutation Side Effects

Mutation 也支援 side effects,你可以在 mutation 完成後執行一些額外的操作。

範例

useMutation({
mutationFn: addTodo,
onMutate: (variables) => {
// A mutation is about to happen!

// Optionally return a context containing data to use when for example rolling back
return { id: 1 };
},
onError: (error, variables, context) => {
// An error happened!
console.log(`rolling back optimistic update with id ${context.id}`);
},
onSuccess: (data, variables, context) => {
// Boom baby!
},
onSettled: (data, error, variables, context) => {
// Error or success... doesn't matter!
},
});

參考資料