最新消息: 电脑我帮您提供丰富的电脑知识,编程学习,软件下载,win7系统下载。

节点给出UnhandledPromiseRejection警告,当我确定*我正在接受拒绝

IT培训 admin 4浏览 0评论

节点给出UnhandledPromiseRejection警告,当我确定*我正在接受拒绝

我正在使用node-libcurl。我有一个小模块,我有一个curl请求队列。以下是实际发出curl请求的函数:

const Curl = require('node-libcurl').Curl;

let timeoutCount = 0;
function _getOData(url) {
    const curl = new Curl();
    return new Promise((resolve, reject) => {
        curl.setOpt(Curl.option.URL, url);
        curl.setOpt(Curl.option.HTTPAUTH, Curl.auth.NTLM);
        curl.setOpt(Curl.option.SSL_VERIFYPEER, false);
        curl.setOpt(Curl.option.SSL_VERIFYHOST, false);
        curl.setOpt(Curl.option.POST, 0);
        curl.setOpt(Curl.option.HTTPHEADER, ['Accept: application/json']);

        let done = false;

        curl.on('end', function (statusCode, body, headers) {
            done = true;
            const retObj = JSON.parse(body);
            resolve(retObj);
            curl.close();
        });

        curl.on('error', function (e) {
            done = true;
            reject(e);
            curl.close();
        });

        curl.perform();

        setTimeout(() => {
            if (!done) {
                timeoutCount++;
                reject(new Error(`request timed out: ${timeoutCount}`));
            }
        },1000*10);
    })
}

我一直在控制台中收到这个错误:(node:26616) UnhandledPromiseRejectionWarning: Unhandled promise rejection (rejection id: 6): Error: request timed out - 所以我添加了timeoutCount,因为我确定我正在捕获所有Promise错误,尽管得到了这个警告。

每次调用_getOData函数都发生在队列逻辑中,特别是这段代码是调用_getOData的唯一代码:

        const p = _getOData(nextObj.url);
        p.then(nextObj.cb);
        p.catch((e) => {
            if (e.message.includes("request timed out")) {
                queue.add(nextObj.url, nextObj.cb, nextObj.ecb);
                return true;
            } else {
                nextObj.ecb(e);
                return false;
            }
        });

所以我在e.message.includes("request timed out")之后设置了一个断点,它每次都会在请求超时错误发生时点击,所以我知道没有“未处理的拒绝承诺”。每一个承诺拒绝都会通过这个捕获。我检查变量是否在那里打破以确保timeoutCount存在,并且它始终是,然后它仍然总是作为未处理的承诺拒绝记录到控制台。

这里发生了什么?

回答如下:

您可能正在捕获队列中的拒绝而不是堆栈上的拒绝。您使用以下代码获得该错误(警告):

var p = Promise.reject("hello world");//do not catch on the stack
setTimeout(
  x=>p.catch(err=>console.log("catching:",err))//caught error on queue
  ,100
);

如果要捕获队列中的拒绝,则可以执行以下操作:

saveReject = p =>{
  p.catch(ignore=>ignore);
  return p;//catch p but return p without catch
}
var p = saveReject(Promise.reject("hello world"));//creating promise on the stack
setTimeout(
  x=>p.catch(err=>console.log("catching:",err))//caught error on queue
  ,100
);

有关队列和堆栈的信息可以在here找到。

节点给出UnhandledPromiseRejection警告,当我确定*我正在接受拒绝

我正在使用node-libcurl。我有一个小模块,我有一个curl请求队列。以下是实际发出curl请求的函数:

const Curl = require('node-libcurl').Curl;

let timeoutCount = 0;
function _getOData(url) {
    const curl = new Curl();
    return new Promise((resolve, reject) => {
        curl.setOpt(Curl.option.URL, url);
        curl.setOpt(Curl.option.HTTPAUTH, Curl.auth.NTLM);
        curl.setOpt(Curl.option.SSL_VERIFYPEER, false);
        curl.setOpt(Curl.option.SSL_VERIFYHOST, false);
        curl.setOpt(Curl.option.POST, 0);
        curl.setOpt(Curl.option.HTTPHEADER, ['Accept: application/json']);

        let done = false;

        curl.on('end', function (statusCode, body, headers) {
            done = true;
            const retObj = JSON.parse(body);
            resolve(retObj);
            curl.close();
        });

        curl.on('error', function (e) {
            done = true;
            reject(e);
            curl.close();
        });

        curl.perform();

        setTimeout(() => {
            if (!done) {
                timeoutCount++;
                reject(new Error(`request timed out: ${timeoutCount}`));
            }
        },1000*10);
    })
}

我一直在控制台中收到这个错误:(node:26616) UnhandledPromiseRejectionWarning: Unhandled promise rejection (rejection id: 6): Error: request timed out - 所以我添加了timeoutCount,因为我确定我正在捕获所有Promise错误,尽管得到了这个警告。

每次调用_getOData函数都发生在队列逻辑中,特别是这段代码是调用_getOData的唯一代码:

        const p = _getOData(nextObj.url);
        p.then(nextObj.cb);
        p.catch((e) => {
            if (e.message.includes("request timed out")) {
                queue.add(nextObj.url, nextObj.cb, nextObj.ecb);
                return true;
            } else {
                nextObj.ecb(e);
                return false;
            }
        });

所以我在e.message.includes("request timed out")之后设置了一个断点,它每次都会在请求超时错误发生时点击,所以我知道没有“未处理的拒绝承诺”。每一个承诺拒绝都会通过这个捕获。我检查变量是否在那里打破以确保timeoutCount存在,并且它始终是,然后它仍然总是作为未处理的承诺拒绝记录到控制台。

这里发生了什么?

回答如下:

您可能正在捕获队列中的拒绝而不是堆栈上的拒绝。您使用以下代码获得该错误(警告):

var p = Promise.reject("hello world");//do not catch on the stack
setTimeout(
  x=>p.catch(err=>console.log("catching:",err))//caught error on queue
  ,100
);

如果要捕获队列中的拒绝,则可以执行以下操作:

saveReject = p =>{
  p.catch(ignore=>ignore);
  return p;//catch p but return p without catch
}
var p = saveReject(Promise.reject("hello world"));//creating promise on the stack
setTimeout(
  x=>p.catch(err=>console.log("catching:",err))//caught error on queue
  ,100
);

有关队列和堆栈的信息可以在here找到。

发布评论

评论列表 (0)

  1. 暂无评论