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

React中使用async/await确保getUsersProduct执行完成后再执行后续代码

异步函数执行顺序问题解决方案

问题背景

现有React代码片段如下:

function login(event) {
  event.preventDefault();
  console.log("*1*");
  let formData = new FormData(event.target);
  ApiRequest.axiosInstance({ method: "post", url: "/login/login.php", data: formData, headers: {} })
    .then(res => {
        console.log("*2*");
        getUsersProduct;
        console.log("*3*");
    })
    .catch((err) => {
        console.error(err);
        console.log("*4*");
    })
    .then(() => {
        console.log("Login Finished");
        console.log("*5*");
    });
}

function getUsersProduct() {
    console.log("*6*");
    ApiRequest.axiosInstance({ method: "post", url: "/login/getUsersProduct.php", data: formData, headers: { "Content-Type": "multipart/form-data" } })
    .then(res => ....
    console.log("*7*");
}

当前控制台输出顺序为 *1* *2* *6* *3*,期望实现顺序为 *1* *2* *6* *7* *3*,即需确保getUsersProduct函数完全执行完成(包括内部异步请求处理及*7*输出)后,再执行后续的console.log("*3*")代码。

解决方案

核心思路是让getUsersProduct返回异步操作的Promise,并在调用时等待其执行完成,async/await是更简洁的实现方式,也可以用Promise链式调用,具体如下:

1. 修正getUsersProduct函数

首先让函数返回axios请求的Promise,同时修复内部formData未定义的问题(需通过参数传入):

function getUsersProduct(formData) {
    console.log("*6*");
    // 返回axios请求的Promise,确保异步操作能被等待
    return ApiRequest.axiosInstance({ 
        method: "post", 
        url: "/login/getUsersProduct.php", 
        data: formData, 
        headers: { "Content-Type": "multipart/form-data" } 
    })
    .then(res => {
        // 这里添加res的业务处理逻辑
        console.log("*7*");
    });
}

2. 在login函数中等待异步操作完成

方式一:使用async/await(推荐,代码可读性更高)

将then的回调函数标记为async,通过await等待getUsersProduct执行完成:

function login(event) {
  event.preventDefault();
  console.log("*1*");
  let formData = new FormData(event.target);
  ApiRequest.axiosInstance({ method: "post", url: "/login/login.php", data: formData, headers: {} })
    .then(async res => {
        console.log("*2*");
        // 等待getUsersProduct的异步操作全部完成
        await getUsersProduct(formData);
        console.log("*3*");
    })
    .catch((err) => {
        console.error(err);
        console.log("*4*");
    })
    .then(() => {
        console.log("Login Finished");
        console.log("*5*");
    });
}

方式二:使用Promise链式调用

若不想用async/await,可以通过嵌套then实现等待:

function login(event) {
  event.preventDefault();
  console.log("*1*");
  let formData = new FormData(event.target);
  ApiRequest.axiosInstance({ method: "post", url: "/login/login.php", data: formData, headers: {} })
    .then(res => {
        console.log("*2*");
        // 链式调用getUsersProduct的Promise,完成后再执行*3*
        return getUsersProduct(formData).then(() => {
            console.log("*3*");
        });
    })
    .catch((err) => {
        console.error(err);
        console.log("*4*");
    })
    .then(() => {
        console.log("Login Finished");
        console.log("*5*");
    });
}

原代码问题分析

原代码中仅写了getUsersProduct;(未调用函数),即使修改为getUsersProduct(),由于内部axios请求是异步操作,函数会先同步执行console.log("*6*")后立即返回,此时then回调会继续执行console.log("*3*"),而axios请求完成后才会输出*7*,导致顺序不符合预期。只有让getUsersProduct返回Promise并等待其完成,才能保证*7*在*3*之前输出。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.27 03:22:04