众所周知,异常捕获是保障服务健壮性常用的手段,node.js也自然支持这一特性。但node.js异步、基于消息的编程方式给异常捕获带来一些困难,请看下面的例子:
process.on('uncaughtException', function(e) {
console.log("exception in uncaughtException:", e);
});
try {
process.nextTick(function () {
throw new Error("exception in nextTick callback");
});
} catch (e) {
console.log("exception in catch:", e);
}
输出:
exception in uncaughtException: [Error: exception in nextTick callback]
可见,try-catch不能捕获回调函数中的异常,也不能捕获事件响应函数中的异常。通常的解决办法是在这些函数中都加入try-catch,但副作用也很明显,一方面增加了代码复杂度和嵌套深度,降低了可读性和可维护性,另一方面v8对于try-catch中的代码优化作用会降低,即牺牲了性能。
node v0.8中新增了domain模块,大大简化异步开发中异常捕获的复杂度,引入domain的代码如下:
var domain = require('domain');
var d = domain.create();
d.on('error', function(e) {
console.log("error in domain:", e);
});
d.run(function () {
process.nextTick(function () {
throw new Error("exception in nextTick callback");
});
});
输出:
error in domain: { [Error: exception in nextTick callback]
domain_thrown: true,
domain: { members: [], _events: { error: [Function] } } }
以上只是一个简单的例子,domain的初衷在于解决异步io的异常处理,只要是注册在domain中event emitters、timer、callback函数,其回调函数中产生的"error"事件和exception都可以被domain捕获。
来看示例:
var domain = require('domain');
var events = require('events');
var d = domain.create();
d.on('error', function(e) {
console.log("error in domain:", e);
});
var e;
d.run(function () {
e = new events.EventEmitter();
});
e.on('msg', function () {
throw new Error("exception in msg callback");
});
e.emit('error', new Error("error msg"));
e.emit('msg');
输出:
error in domain: { [Error: error msg]
domain_emitter:
{ domain: { members: [], _events: [Object] },
_events: { msg: [Function] } },
domain: { members: [], _events: { error: [Function] } },
domain_thrown: false }
error in domain: { [Error: exception in msg callback]
domain_thrown: true,
domain: { members: [], _events: { error: [Function] } } }
注意不是EventEmitter所有成员函数中的exception都可以被自动捕获,如果成员函数不是在事件响应函数中执行,并且未跟domain绑定,就不会被domain捕获。
示例:
var domain = require('domain');
var events = require('events');
var d = domain.create();
d.on('error', function(e) {
console.log("error in domain:", e);
});
var e;
d.run(function () {
e = new events.EventEmitter();
});
e.f = function () {
throw new Error("exception in member function");
};
e.f();
如果在domain.run()中执行,或跟domain绑定,是可以被捕获的:
d.run(function () {
e.f();
});
domain还有其他接口,用于绑定对象、函数等,请参考官方文档:
http://nodejs.org/api/domain.html
转帖:http://blog.sina.com.cn/s/blog_70000469010134wr.html
domain: node.js的异常捕获利器相关推荐
- js的异常捕获try和catch语句
js里也可以使用try{}catch(){}语句块.看范例: 1.js出错则问询是否继续查看 Code: <script type="text/javascript"> ...
- node.js 使用domain模块捕获异步回调中的异常
和其他服务器端语言相比,貌似node.js 对于异常捕捉确实非常困难. 首先你会想到try/catch ,但是在使用过程中我们会发现并没有真正将错误控制在try/catch 语句中. 为什么? 答案是 ...
- Node.js 在微医的应用场景及实践
我是来自微医集团消费事业群的前端工程师高翔,这篇文章整理自我在<第一届缤纷前端技术沙龙>的主题分享<Node.js 在医疗行业的应用>,介绍了 Node.js 在微医的发展历程 ...
- 【特别推荐】Node.js 中文学习资料和教程导航
这篇文章来自 Github 上的一位开发者收集整理的 Node.js 中文学习资料和教程导航.Node 是一个服务器端 JavaScript 解释器,它将改变服务器应该如何工作的概念,它的目标是帮助程 ...
- 如何将命令行参数传递给Node.js程序?
我有一个用Node.js编写的Web服务器,我想使用一个特定的文件夹启动. 我不确定如何在JavaScript中访问参数. 我正在像这样运行节点: $ node server.js folder 这是 ...
- Node.js异常捕获处理
文章目录 Node.js异常特点 异常的捕获处理 同步异常 异步异常 callback event Promise Async/Await uncaughtException异常 Node.js异常特 ...
- Node.js Domain 模块
Node.js 工具模块 Node.js Domain(域) 简化异步代码的异常处理,可以捕捉处理try catch无法捕捉的异常.引入 Domain 模块 语法格式如下: var domain = ...
- atitit.js浏览器环境下的全局异常捕获
atitit.js浏览器环境下的全局异常捕获 window.onerror = function(errorMessage, scriptURI, lineNumber) { var s= JSON. ...
- js监听多个事件_JavaScript中的事件与异常捕获解析
这篇文章主要给大家介绍了关于JavaScript中事件与异常捕获的相关资料,文中通过示例代码介绍的非常详细,写的十分的全面细致,具有一定的参考价值,对此有需要的朋友可以参考学习下.如有不足之处,欢迎批 ...
最新文章
- 太赞了!NumPy 手写所有主流 ML 模型,由普林斯顿博士后 David Bourgin打造的史上最强机器学习基石项目!...
- linux修改系统时间为北京时间(CentOS)
- 通过AAA服务器使用XML文件为远程接入SSL ***认证授权
- 1.8 ionic3入门——测滑菜单(side menu)中的界面跳转
- 【Linux】一步一步学Linux——readonly命令(219)
- 基于互联网大数据的管理创新
- Java使用Apache CXF开发Web Service
- 计组之存储系统:4、双口RAM和多模块存储器(存取周期、双端口RAM、多体并行存储器、存储体)
- Python int() 函数
- 他,用了14年,从初代豆瓣工程师到AI公司CTO,创业心一直未变
- 源码:winamp播放器 C++
- 计算机属性资源管理器已停止工作,windows资源管理器已停止工作,教您windows资源管理器已停止工作如何解决...
- 关于Gitlab恼人的Git无权限访问问题解决
- 初中作文计算机想象作文,初中想象作文600
- ThinkPHP实现定时执行任务的两种方法
- 僵尸网络新世界:摄像头的背叛和战争
- :hover的几种选择用法
- MySQL数据导出与导入
- C语言自动识别文本编码
- 1995年的一次访谈中,乔布斯谈到处于垄断地位的科技公司因为营销人员掌握了话语权,不再注重产品研发而衰败
热门文章
- 【蓝桥杯2018JavaB】螺旋折线
- Ultraman 奥特曼名字
- Result Maps collection already contains value for问题
- Sui主网升级至V1.2.0版本
- 面向对象--02面向对象的三个基本特征
- Apollo 配置中心源码分析
- Android12修改关机菜单按键触发方式
- 微电网与电动车蓄电池优化(Matlab代码实现)
- Jersey框架:统一异常处理
- 企业微信获取用户信息响应40029(微信小程序与公众号出现类似问题应该是同样的原因)