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

Node.js Express异步函数结果集无法取值 无法生成嵌套JSON结构

问题原因
  1. 被async修饰的getAlternativeProducts函数默认返回Promise对象,调用时没有添加await关键字等待异步操作完成,所以拿到的是处于pending状态的Promise实例,而非执行完成后的替代商品结果集。
  2. 接口响应流程没有等待所有替代商品的异步查询操作完成,就提前执行了res.json(structured)返回数据,此时替代商品的查询还在执行中,返回的结果自然没有对应数据。
  3. 额外问题:使用全局变量structured存储结果会存在并发请求冲突问题,多个用户同时调用接口时,全局变量会被互相覆盖,导致返回结果错乱。另外你给出的预期JSON结构中alternateproducts外层的{}属于语法错误,正确结构应该直接是数组类型。
修复代码
// 移除全局structured变量
app.route('/products')
// GET endpoint
.get(cors(), async function(req, res) {
    try {
        const request = new appmodule.sql.Request();
        // 异步查询所有主商品
        const recordset = await request.query('SELECT * FROM Products');
        // 等待嵌套结构组装完成
        const structuredResult = await GenerateStructuredJSON(recordset);
        res.json(structuredResult);
    } catch (err) {
        console.error(err);
        res.status(500).json({msg: '数据查询失败'});
    }
});

async function GenerateStructuredJSON(recordset) {
    const products = recordset.recordset;
    return await getNestedProducts(products);
}

async function getNestedProducts(prod) {
    for(let i = 0; i < prod.length; ++i) {
        const productId = prod[i].Id;         
        // 添加await等待替代商品查询完成
        const alternativeproducts = await getAlternativeProducts(productId);
        // 仅当存在替代商品时添加对应字段
        if(Array.isArray(alternativeproducts) && alternativeproducts.length > 0) {
            prod[i].alternateproducts = alternativeproducts;
        }
    }
    return prod;
}

async function getAlternativeProducts(prodID) {
    const request = new appmodule.sql.Request();
    request.input('prodid', appmodule.sql.Int , prodID);
    const queryRes = await request.query(
        'SELECT Products.* FROM Products ' +
        'RIGHT JOIN ProductAlternatives ON ProductAlternatives.AlternativeProductId=Products.Id ' +
        'WHERE ProductAlternatives.ProductId=@prodid'
    );
    return queryRes.recordset;
}
性能优化建议

当前实现存在N+1查询问题:每有一个主商品就会发起一次数据库查询请求,当商品数量较多时性能会很差。建议将两次查询合并为一次联表查询,一次性拿到所有主商品和对应替代商品数据,再在内存中组装成需要的嵌套结构,大幅减少数据库交互次数。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.10.05 00:30:04