TypeScript中Awaited<R>未解包为R的Axios响应类型问题
解决TypeScript中Awaited不存在data属性的问题
问题根源
你遇到的错误核心是泛型R缺少明确的类型约束——尽管你给它设置了默认值AxiosResponse<T>,但TypeScript允许调用时传入任意类型,导致编译器无法确定Awaited<R>必然包含data属性。
修复方案
给泛型R添加继承约束,强制它必须是AxiosResponse<T>的子类型,这样编译器就能确定返回的response一定拥有data属性:
export const fetchWithRetry = async < T = any, Q = Record<string, string>, R extends AxiosResponse<T> = AxiosResponse<T> // 添加extends约束 >( route: string, queryParams: Partial<Q> = {}, ) => { const response = await fetchResponseWithRetry<T, Q, R>(route, queryParams) return response.data; // 错误消失 }; export const fetchResponseWithRetry = async < T = any, Q = Record<string, string>, R extends AxiosResponse<T> = AxiosResponse<T>, // 同样添加约束 >( route: string, queryParams: Partial<Q> = {}, ) => { try { const options: AxiosRequestConfig = { headers: { "Content-Type": "application/json", }, params: { ...queryParams } as Q, // 替换不安全的类型断言 }; return (await axios.get<T, R, unknown>(route, options)); } catch (error) { if (error instanceof Error) { buildLogger(`${error.message}`); if (error instanceof AxiosError) buildLogger(`${error.request.url}`); } } throw new Error(`This should never be reached.`); };
额外优化建议
如果不需要自定义R类型,可以直接省略该泛型参数,让Axios自动推导返回类型,代码会更简洁:
export const fetchWithRetry = async < T = any, Q = Record<string, string> >( route: string, queryParams: Partial<Q> = {}, ) => { const response = await fetchResponseWithRetry<T, Q>(route, queryParams) return response.data; }; export const fetchResponseWithRetry = async < T = any, Q = Record<string, string> >( route: string, queryParams: Partial<Q> = {}, ) => { try { const options: AxiosRequestConfig = { headers: { "Content-Type": "application/json", }, params: { ...queryParams } as Q, }; return axios.get<T>(route, options); // Axios自动推导AxiosResponse<T>类型 } catch (error) { if (error instanceof Error) { buildLogger(`${error.message}`); if (error instanceof AxiosError) buildLogger(`${error.request.url}`); } } throw new Error(`This should never be reached.`); };
内容的提问来源于stack exchange,提问作者webstackdev
相关产品推荐
相关产品推荐

