域可以嵌套在node.js中吗?

B T*_*B T 4 error-handling node.js node.js-domains

使用同步错误,您可以嵌套如下错误范围:

try {
  try {
    throw Error('e')
  } catch(e) {
    if(e.message !== 'f')
      throw e
  }
} catch(e) {
  handleError(e)
}
Run Code Online (Sandbox Code Playgroud)

这是我希望它能起作用的方式,但是却没有(似乎在域错误处理程序内部的错误被抛出到顶部,跳过了两者之间的任何域):

var domain = require('domain');
var dA = domain.create();
dA.on('error', function(err) {
    console.log("dA: "+ err); // never happens
});
dA.run(function() {
    var dB = domain.create();
    dB.on('error', function(err) {
        throw err
    });
    dB.run(function() {
        setTimeout(function() {
            console.log('dB')
            throw 'moo'
        },0)
    });
});
Run Code Online (Sandbox Code Playgroud)

有办法做到这一点吗?

oth*_*m23 5

通过重新抛出,冒泡在域中不起作用。如果要将错误传递给您知道可以处理错误的另一个域,则可以直接在该域上重新发送错误事件:

var domain = require('domain');
var dA = domain.create();
dA.on('error', function(err) {
    console.log("dA: "+ err); // never happens
});
dA.run(function() {
    var dB = domain.create();
    dB.on('error', function(err) {
        dA.emit('error', err);
    });
    dB.run(function() {
        setTimeout(function() {
            console.log('dB')
            throw 'moo'
        },0)
    });
});
Run Code Online (Sandbox Code Playgroud)

稍微扩展一下,从域的错误处理程序引发的问题是它直接传播到顶层,而更令人困惑的是,如果引发是错误处理程序中的错误导致的结果,则是打印的堆栈跟踪out来自您的原始错误,而不是处理程序中的错误。从理论上讲,可以将异常冒泡到堆栈上,但这不是域设计的方式。

在“嵌套”域名将正常工作,如果外域的处理程序抛出,而内域是活动的,但它的作用在这种情况下是给错误外域的错误处理程序,然后退出这两个外部和嵌套域。这模仿了try / catch情况下catch如何展开堆栈,但可能会有些混乱。

  • 这非常令人困惑,我认为这是域设计中的主要缺陷 (4认同)