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

异步函数(API调用)顺序执行失败问题排查

顺序API调用异常问题分析与解决

问题现象

需要依次执行两个API调用:

  1. 先发送POST请求创建新游戏,获取返回的code值
  2. 再用这个code发送GET请求获取对应游戏数据

但实际运行出现异常:

  • POST请求返回的code是ST231,但finally中打印的code状态为空
  • GET请求返回的却是code为BX892的游戏数据,并非刚创建的游戏

原因分析

  1. React状态更新的异步性:setNewCode是异步操作,调用后不会立刻更新code变量。finally中打印的是当前闭包捕获的初始code值(空字符串),而非刚设置的新值。
  2. 闭包捕获旧值:useEffect的依赖数组为空,意味着asyncFunction只会在组件首次渲染时执行,它捕获的是组件初始化时的code状态(空字符串)。此时发送GET请求时,拼接的路径是/games/(空code),API可能返回了默认数据或之前创建的游戏数据(比如BX892)。

解决方法

不需要通过React状态传递API调用的中间值,直接将POST返回的code存到普通变量中,用于后续GET请求:

const dateTime = new Date().toJSON();
const [code, setNewCode] = useState("");
const [gameData, setGameData] = useState<any>([]);

useEffect(() => {
  const asyncFunction = async () => {
    try {
      // 发送POST请求并获取返回的code
      const postResponse = await axios.post(apiUrl + "/games", {
        game: {
          name: dateTime,
        },
      });
      const gameCode = postResponse.data.code;
      console.log(gameCode); // 此处打印ST231
      setNewCode(gameCode); // 若需渲染该code,再更新状态

      // 用普通变量gameCode发送GET请求
      const getResponse = await axios.get(apiUrl + "/games/" + gameCode);
      console.log(JSON.stringify(getResponse.data));
      setGameData(getResponse.data); // 直接存储原始数据,无需转字符串
      console.log("Get is done");
    } catch (error) {
      console.error(error);
    }
  };
  asyncFunction();
}, []);

额外优化点

  • 避免混合使用await和.then/.catch,统一用async/await写法,代码更简洁易读
  • gameData的类型定义为any[],但返回的是单个游戏对象,建议修正类型为any或具体的游戏类型
  • 不要将getResponse.data转成字符串后存入状态,直接存原始对象更便于后续使用

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.30 13:18:09