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

Promise与异步操作问题:二次请求提前执行的技术求助

问题根源分析

你遇到的核心问题是第一个异步请求updatePU没有被正确等待。看一下你的代码:

const promise = new Promise((resolve, reject) => { resolve(this.updatePU(name, 'text', selectedOption.code)); })

这里你手动创建了一个Promise,但updatePU是异步函数,它内部调用了fetch却没有返回这个异步操作的Promise链。所以当你调用resolve(this.updatePU(...))时,resolve接收的其实是undefined(因为updatePU没有返回值),导致这个手动创建的Promise立刻就变成了resolved状态,直接执行后面的then回调——完全没等updatePU的请求完成。

解决方案

我们只需要两步就能修复这个问题:

1. 让updatePU返回它的Promise链

修改updatePU函数,在fetch前面加上return,这样整个函数会返回异步操作的Promise,外部就能等待它完成:

updatePU = (name, type, value) => {
    const PUOrderNo = this.props.puOrderNo;
    const updatedValue = type === 'text' ? (`'${name}': '${value}'`) : (`'${name}': ${value}`);
    
    // 关键:返回fetch的Promise链
    return fetch('/ModifyPUOrder', {
        crossDomain: true,
        method: 'POST',
        headers: {
            'Accept': 'application/json',
            'Content-Type': 'application/json',
        },
        body: JSON.stringify({ updatedValue: updatedValue, puOrderNo: PUOrderNo }),
    })
    .then(response => {
        if(response.ok){
            return response.json();
        } else {
            console.log(response);
            throw new Error('Request failed!');
        }
    }, networkError => { 
        console.log(networkError.message);
        throw networkError; // 抛出错误,让外部catch能捕获到
    })
    .then(data => {
        if ("error" in data) {
            alert(data.error.message);
            this.refresh();
        }
        this.props.updatePUOrderForm(data);
    });
}

2. 直接使用updatePU返回的Promise,去掉手动创建的Promise

现在updatePU已经返回Promise了,我们可以直接链式调用then,不需要再手动包裹Promise:

this.updatePU(name, 'text', selectedOption.code)
.then(() => {
    console.log('Calling checkExpress function');
    const puOrderNo = this.props.puOrderNo;
    
    // 这里也建议return这个fetch的Promise,让错误能被外部catch捕获
    return fetch('/CheckExpress', {
        crossDomain: true,
        method: 'POST',
        headers: {
            'Accept': 'text/xml',
            'Content-Type': 'application/json',
        },
        body: JSON.stringify({"puOrderNo": puOrderNo })
    })
    .then(response => response.text())
    .then(str => convert.xml2json(str)) // 可以直接返回,不用存到变量里
    .then(express => {
        const data = JSON.parse(express);
        const checkExpress = data['elements'][0].elements[0].elements[0].elements[0].elements[0].text;
        console.log('checkExpress:', checkExpress);
        // 简化写法
        this.props.updatePackageTypeField(checkExpress === 'true');
    })
})
.catch(err => console.log('Request error:', err)); // 统一捕获所有错误
额外优化点
  • 去掉了不必要的变量express,直接在then中传递转换后的结果,代码更简洁。
  • 统一了错误捕获,把两个请求的错误都放到最外层的catch里处理,避免遗漏。
  • 在updatePU的networkError回调里添加了throw networkError,确保网络错误能被外层捕获。

这样修改后,第一个请求updatePU完成后才会执行第二个CheckExpress请求,顺序就正确了。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.05.13 08:33:10