question:使用同一请求数据且渲染顺序不确定时复用
问题:组件A和组件B都用某个请求的数据,但是不知道组件A和组件B谁先渲染,怎么设计请求函数可以复用数据?
答案:通过缓存请求状态和复用 Promise来设计请求函数,确保无论哪个组件先发起请求,最终都能共享同一份数据。关键是:Map数据结构缓存请求
// 缓存对象:key为请求标识(如URL),value为{ promise: 请求的Promise, data: 缓存的数据 }
const requestCache = new Map();/*** 复用请求的工具函数* @param {string} key - 请求的唯一标识(如API地址)* @param {Function} requestFn - 实际发起请求的函数(返回Promise)* @returns {Promise} - 返回请求的Promise,确保同一key的请求只发起一次*/
export function fetchSharedData(key, requestFn) {// 如果缓存中已有该请求,直接返回缓存的Promiseif (requestCache.has(key)) {const { promise } = requestCache.get(key);return promise;}// 发起新请求,并缓存Promiseconst promise = requestFn().then((data) => {// 请求成功后,更新缓存中的数据requestCache.set(key, { promise, data });return data;}).catch((error) => {// 请求失败时,清除缓存(允许重试)requestCache.delete(key);throw error; // 抛出错误供组件捕获});// 先缓存Promise(此时请求可能还在进行中)requestCache.set(key, { promise, data: null });return promise;
}
使用
// 假设这是实际的API请求函数
function fetchUserInfo() {return fetch('/api/user').then(res => res.json());
}// 组件A或者B
function ComponentA() {const [user, setUser] = React.useState(null);React.useEffect(() => {// 用key='userInfo'标识请求,确保和另一个组件复用fetchSharedData('userInfo', fetchUserInfo).then(data => setUser(data)).catch(err => console.error('请求失败:', err));}, []);return <div>组件A: {user?.name}</div>;
}