Node.js Uncaught TypeError:callback不是process.nextTick中的函数

时间:2014-01-16 23:41:03

标签: node.js event-loop

我收到以下错误。它显然来自传递给process.nextTick的回调。鉴于堆栈跟踪几乎无法使用,我该如何调试?幕后发生了什么,我怎样才能在更大的项目中解决这个问题?

TypeError: callback is not a function
    at nextTickCallbackWith0Args (node.js:420:9)
    at process._tickDomainCallback (node.js:390:13)

N.B。较旧版本的Node具有不同的process.nextTick实现,并吐出以下堆栈跟踪。

Uncaught TypeError: undefined is not a function
    at process._tickCallback (node.js:415:13)

1 个答案:

答案 0 :(得分:6)

如果传递给process.nextTick的函数在勾选后不是函数,则Node.js tick回调更喜欢抛出错误,而不是在第一次调用它时告诉你。

在勾选后调用函数的地方:

// this will print "hi!", followed by "hello there"
process.nextTick(function() {
  console.log('hello there');
});
console.log('hi!');

在下一次打勾之前,非功能实际上并不重要:

// this will just print "hi!", and an error will be thrown later on
process.nextTick(undefined);
console.log('hi!');

下面,我将概述两个可用于追踪罪魁祸首的诊断工具。

工具1:longjohn

事实证明,这种情况很常见,以至于存在一个工具来扩展堆栈跟踪,其中包含来自先前滴答的信息。

只需在流程开始时安装longjohn(可用on npm)和require即可。这将产生类似于以下的堆栈跟踪:

TypeError: Cannot read property 'apply' of undefined
    at nextTickCallbackWith0Args (node.js:420:9)
    at process._tickCallback (node.js:349:13)
    at Function.Module.runMain (module.js:443:11)
    at startup (node.js:139:18)
    at node.js:968:3
---------------------------------------------
    at Object.<anonymous> (.../example.js:3:9)
    at Module._compile (module.js:409:26)
    at Object.Module._extensions..js (module.js:416:10)
    at Module.load (module.js:343:32)
    at Function.Module._load (module.js:300:12)
    at Function.Module.runMain (module.js:441:10)
    at startup (node.js:139:18)
    at node.js:968:3

现在你有了一个有用的堆栈跟踪,你可以使用你的调试技巧找出你给定process.nextTick未定义而不是函数的原因。

猴子补丁

因为javascript是动态的,我们可以轻松设置新版本的process.nextTick(也就是说,我们可以monkey patch)跟踪对它的调用,但代理真正的nextTick函数:< / p>

var nextTick = process.nextTick;

process.nextTick = function(callback) {
  if (typeof callback !== 'function') {
    console.trace(typeof callback + ' is not a function');
  }
  return nextTick.apply(process, arguments);
};

注意:我不建议为生产代码执行此操作,但它确实可以更轻松地找到除了process.nextTick函数之外的其他内容。请记住,这是修改全局process变量,因此它可能会在某个时刻中断,并且它当然不被认为是最佳实践,但它可以很好地找到小问题。 (附录:自从我最初写这篇文章以来,我不得不修改它,因为它曾经破了一次。)

Trace: undefined is not a function
    at process.nextTick (.../example.js:5:13)
    at Object.<anonymous> (.../example.js:10:9)
    at Module._compile (module.js:409:26)
    at Object.Module._extensions..js (module.js:416:10)
    at Module.load (module.js:343:32)
    at Function.Module._load (module.js:300:12)
    at Function.Module.runMain (module.js:441:10)
    at startup (node.js:139:18)
    at node.js:968:3

如上所述,既然你有一个有用的堆栈跟踪,你就可以找出根本原因。

就内部而言,请查看the source old link_tickCallback node.js内的{{1}}功能。