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

使用useQuery时同组件双GET请求异常,拆分组件解决后求原因

问题原因分析

你遇到的问题核心是浏览器拦截了第二个请求,导致它卡在预检(OPTIONS)阶段,同时显示“Provisional Headers are shown”,拆分到独立组件后恢复正常,主要有这几个可能的原因:

1. useQuery 缓存Key重复

如果两个useQuery的缓存标识(第一个参数)完全一样,react-query会判定这是同一个请求,自动取消后发起的那个,转而复用缓存数据。这种情况下浏览器会直接终止第二个请求,就会出现你看到的现象。

  • 检查两个useQuery的第一个参数:
    // 错误示例:共用了相同的缓存key
    useQuery(['user'], fetchUserInfo)
    useQuery(['user'], fetchUserOrders)
    
    改成不同的key就能解决:
    useQuery(['user-info'], fetchUserInfo)
    useQuery(['user-orders'], fetchUserOrders)
    

2. 第二个请求触发跨域预检但未通过

正常GET请求属于「简单请求」,不会触发OPTIONS预检,但如果你的第二个请求满足以下任一条件,浏览器会先发送OPTIONS预检:

  • 带了非简单请求头(比如自定义的X-Request-Id,或者Content-Type不是application/x-www-form-urlencoded、multipart/form-data、text/plain)
  • 请求URL包含特殊路径/参数,被浏览器判定为非简单请求
    当预检请求被服务器拒绝(比如服务器没配置CORS允许该请求的预检),浏览器就会终止实际的GET请求,显示“Provisional Headers are shown”。

拆分组件后,可能因为渲染时机不同,请求头/参数被间接修正,避免了预检触发;或者react-query在组件分离后,请求执行逻辑被隔离,不会出现请求头被意外篡改的情况。

3. useQuery 执行时机冲突

如果两个useQuery的enabled配置存在依赖,或者其中一个请求的取消逻辑影响了另一个:

  • 比如第一个请求的enabled依赖第二个请求的返回值,导致第二个请求被提前取消
  • 或者组件内的状态更新,触发其中一个请求重新执行,进而取消了另一个请求

这种情况下请求是被react-query主动取消的,浏览器会显示“Provisional Headers are shown”,因为请求没有正常走完流程。

4. 全局请求拦截器的干扰

如果你用了axios、fetch的全局拦截器,可能在同一个组件发两个请求时,拦截器对第二个请求做了错误修改(比如添加了不符合CORS规则的头),导致触发预检且失败。拆分组件后,拦截器的执行上下文变化,避开了这个问题。

验证建议
  • 先排查缓存key是否唯一,这是最常见的触发原因
  • 对比同一个组件和拆分组件时,第二个请求的请求头差异,看是否有非简单请求头
  • 检查服务器CORS配置,确认是否允许该请求的OPTIONS预检
  • 临时禁用全局请求拦截器,看问题是否消失

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.06.19 19:37:09