【问题标题】:Chain promises and decorate an object链式承诺和装饰对象
【发布时间】:2018-11-08 16:48:30
【问题描述】:

我正在尝试理解 Promise,我需要将它们链接起来并装饰来自不同端点的对象宽度数据。

例如:

我的 node-express 应用中有这个

//controller.js
export const getItem = (req, res) => {
    ItemService.getItem(req.params.id).then(function(item) {
        return res.json({ 'success': true, 'message': 'Item found successfully', 'item': item});
    }).catch(function(result) {
        return res.json({ 'success': false, 'errorMessage': 'Ups!' });
    });
};

//itemService.js
export const getItem = function(id){
    return new Promise(function(resolve, reject) {
        fetch(apiUrls.getItem(id))
            .then(response => {
                if(response.ok){
                    response.json().then(data => {
                        resolve(data);
                    })
                } else {
                    reject(response.err);
                }
            });
    });
};

所以我想要完成的是在resolve语句之前装饰数据。实际上,我想对不同的 API 进行其他获取,并使用来自该响应的数据来装饰我首先谈论的数据。我会写一些伪代码:

fetch (api1)
   responseApi1 //{id: 123, name: 'Mike'}
   fetch (api2)
      responseApi2
      responseApi1.description = responseApi2.description
      responseApi1.address = responseApi2.address

  return responseApi1 //responseApi1 decorated width responseApi2

//Controller
return res.json({ 'success': true, 'message': 'Item found successfully', 'item': responseApi1});

我根本不懂promise,不能做出这个promise链,通过这个promise只装饰一个对象并返回它。

【问题讨论】:

  • 两个脚本都导出了一个名为getItem的函数,另外还有一个对象apiUrls,它的属性函数为getItem?你可能会考虑给函数命名更独特,否则很容易混淆自己
  • fetch 已经是一个承诺,不要做return new Promise,只做return fetch( & 然后就做-> if (response) return response.json(); else throw response.errr;
  • 如果api2不依赖api1,我建议使用Promise.all

标签: javascript node.js express promise fetch-api


【解决方案1】:

回答您的“伪代码”示例(假设两个 api 都返回 JSON)

return fetch (api1)
    .then(res => res.json())
    .then(responseApi1 => fetch(api2)
        .then(res => res.json())
        .then(({descritpion, address}) => ({...responseApi1, description, address}))
    )
    .then(result => {
        //result is responseApi1 decorated width responseApi2
    });

或者,如果 api2 不依赖 api1 的结果(从您的伪代码中不清楚)

return Promise.all(fetch(api1).then(res => res.json()), fetch(api2).then(res => res.json()))
    .then((responseApi1, {descritpion, address}) => ({...responseApi1, description, address}));

不过,我不确定伪代码中的 controller 部分是什么意思 - 就像你拥有它一样毫无意义

【讨论】:

  • 就像你说的,api2不依赖api1的结果。我只需要调用一堆 API 并从这些响应中获取对象宽度信息。
  • 所以使用promise all方法
猜你喜欢
  • 2017-12-18
  • 1970-01-01
  • 1970-01-01
  • 2018-09-19
  • 2016-03-31
  • 2017-03-13
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多