You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

React中如何在多组件中使用RTK Query的mutation响应数据

RTK Query Mutation响应跨组件无法访问的解决方案

问题背景

使用React 18 + @reduxjs/toolkit 1.9.1开发,表单提交时通过RTK Query的artistSearch mutation触发POST接口,当前组件能正常拿到响应数据并完成页面跳转,但跳转后的目标组件及其他组件无法获取该mutation的响应数据。调用useArtistSearchMutation后打印返回的data结果为undefined。

相关代码

表单提交逻辑:

const formSubmit = async (data) => {
  const payload = {
    ...
  };

  try {
    const response = await artistSearch(payload);

    if (response) {
      navigate("/artist-search-results", { state: { data } });
    }
  } catch (artistError) {
    ...
  }
};

API定义:

export const artistApi = createApi({
  reducerPath: "artistApi",
  baseQuery: fetchBaseQuery({
    baseUrl: `...`,
    headers: { ... },
  }),
  endpoints: (builder) => ({
    getArtist: builder.query({
      query: (uid) => `/getProfile/${uid}`,
    }),
    artistSearch: builder.mutation({
      query: (formData) => ({
        url: "ArtistListSearch",
        method: "POST",
        body: formData,
      }),
    }),
  }),
});

export const { useGetArtistQuery, useArtistSearchMutation } = artistApi;

目标组件尝试获取数据的代码:

const [
  artistSearch,
  {
    data: artistSearchResponse,
    error: artistError,
    isLoading: isArtistLoading
  }
] = useArtistSearchMutation();
console.log("artist search data is:", artistSearchResponse);

原因分析

RTK Query的mutation默认不会全局缓存响应结果,它的状态是组件级别的——只有发起mutation的组件实例能拿到本次调用的响应,其他组件重新调用useArtistSearchMutation时,只会拿到新的初始状态(data为undefined),无法获取之前的调用结果。

解决方法

方法1:路由跳转时传递响应数据

最直接的方式是在跳转时把mutation的响应数据通过路由state传递给目标组件,适合一次性使用的场景:

const formSubmit = async (data) => {
  const payload = { ... };
  try {
    const response = await artistSearch(payload);
    if (response) {
      // 传递mutation返回的响应数据,而非原表单数据
      navigate("/artist-search-results", { state: { artistData: response.data } });
    }
  } catch (artistError) { ... }
};

目标组件中通过useLocation获取数据:

import { useLocation } from 'react-router-dom';

const ArtistSearchResults = () => {
  const location = useLocation();
  const artistData = location.state?.artistData;
  
  console.log('artist search data is:', artistData);
  // 后续逻辑处理
};

方法2:手动将mutation结果缓存到RTK Query的全局缓存

如果需要在多个组件中长期访问,可以通过onQueryStarted钩子把mutation的响应存入RTK Query的query缓存中:

artistSearch: builder.mutation({
  query: (formData) => ({
    url: "ArtistListSearch",
    method: "POST",
    body: formData,
  }),
  // 查询完成后,将响应缓存到getArtist接口的指定key下
  onQueryStarted: async (arg, { queryFulfilled, dispatch }) => {
    const { data } = await queryFulfilled;
    // 这里的'search_result'是自定义的缓存key,可根据需求修改
    dispatch(
      artistApi.util.updateQueryData('getArtist', 'search_result', () => data)
    );
  },
}),

然后在其他组件中通过useGetArtistQuery获取缓存数据:

// skip设为false确保直接读取缓存
const { data: artistSearchResponse } = useGetArtistQuery('search_result', { skip: false });
console.log('artist search data is:', artistSearchResponse);

方法3:存入Redux全局状态

如果需要更灵活的全局状态管理,可以创建自定义Redux slice来存储mutation响应:

  1. 创建slice:
import { createSlice } from '@reduxjs/toolkit';

const artistSearchSlice = createSlice({
  name: 'artistSearch',
  initialState: {
    result: null,
  },
  reducers: {
    setArtistSearchResult: (state, action) => {
      state.result = action.payload;
    },
    clearArtistSearchResult: (state) => {
      state.result = null;
    },
  },
});

export const { setArtistSearchResult, clearArtistSearchResult } = artistSearchSlice.actions;
export default artistSearchSlice.reducer;
  1. 在store中注册该slice(确保store已配置RTK Query的middleware)。

  2. 提交表单时dispatch保存数据的action:

import { useDispatch } from 'react-redux';
import { setArtistSearchResult } from './path/to/artistSearchSlice';

const formSubmit = async (data) => {
  const dispatch = useDispatch();
  const payload = { ... };
  try {
    const response = await artistSearch(payload);
    if (response) {
      dispatch(setArtistSearchResult(response.data));
      navigate("/artist-search-results");
    }
  } catch (artistError) { ... }
};
  1. 其他组件通过useSelector获取数据:
import { useSelector } from 'react-redux';

const ArtistSearchResults = () => {
  const artistSearchResponse = useSelector(state => state.artistSearch.result);
  console.log('artist search data is:', artistSearchResponse);
};

内容的提问来源于stack exchange,提问作者neil

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.01 19:43:20