如何承诺此功能-nodejs [重复]

Posted

技术标签:

【中文标题】如何承诺此功能-nodejs [重复]【英文标题】:How to Promisify this function - nodejs [duplicate] 【发布时间】:2016-04-16 15:46:43 【问题描述】:

我有一个需要返回承诺的 ajax 调用。函数如下

client.tickets.create(ticket,  function(err, req, result) 
  if (err)     
    logger.error(err);

    return false;
  

  return JSON.stringify(result);
);

我必须等待这个函数执行,然后才能执行下一个操作。我怎样才能保证这个功能?

我尝试了以下操作,但它给了我一个错误提示 Cannot call method then of undefined:

return client.tickets.create(ticket).then(function(result)
    return JSON.stringify(result);
,function(err)
    logger.error(err);
    return false;
);

【问题讨论】:

你用什么promise api? 【参考方案1】:

您有错误,因为create() 不是 Promise。承诺一个异步函数非常容易(nodejs 现在有一个内置的 Promise 支持):

function createTicket(ticket) 
    // 1 - Create a new Promise
    return new Promise(function (resolve, reject) 
        // 2 - Copy-paste your code inside this function
        client.tickets.create(ticket, function (err, req, result) 
            // 3 - in your async function's callback
            // replace return by reject (for the errors) and resolve (for the results)
            if (err) 
                reject(err);
             else 
                resolve(JSON.stringify(result));
            
        );
    );


// 4 - consume your promise with then() (resolved promise) and catch (rejected promise)
createTicket(ticket).then(function (result) 
    // deal with result here
).catch(function (err) 
    // deal with error here
);

【讨论】:

在 Node.js 8.0.0 的候选版本中,有一个新的实用程序 util.promisify,它封装了承诺任何功能的能力。它与其他答案中建议的方法没有太大区别,但具有作为核心方法的优势。您可能想了解更多in this post【参考方案2】:

我建议您使用 Bluebird 之类的库来为您执行此操作,而不是手动将异步代码包装到 Promise 中:

var Bluebird = require('bluebird');

//either 
client.tickets = Bluebird.promisifyAll(client.tickets);
//or 
client.tickets.createAsync = Bluebird.promisify(client.tickets.create);
...
    return client.tickets.createAsync(ticket)
      .then(JSON.stringify)
      .catch(err => 
        logger.error(error); 
        return false
      );

【讨论】:

【参考方案3】:
function createTicket()
var deferred = Q.defer()
client.tickets.create(ticket,  function(err, req, result) 
     if (err)  
                logger.error(err);
                return deferred.reject(err)
            
   return deferred.resolve(result)
);


createTicket().then(function()
    //success here
, function()
    //failure here
);

使用 Q api 你可以实现承诺。

【讨论】:

以上是关于如何承诺此功能-nodejs [重复]的主要内容,如果未能解决你的问题,请参考以下文章

如何隐瞒回调的承诺? [重复]

暂停功能,直到承诺解决[重复]

测试时出现“mpromise(猫鼬的默认承诺库)已弃用”错误[重复]

那么如何在承诺中添加延迟[重复]

如何按顺序执行承诺并返回所有结果[重复]

NodeJS / Firebase中的自动任务[重复]