我开始在我的javascript对象中添加错误处理,这些对象经常使用jQuery。 我遇到的问题是,当我从jQuery方法中抛出新的错误时 - 它不会被包装jquery调用的catch语句捕获 - 它只是抛出标准错误,但不会作为日志消息登录到控制台。这是一个例子:
var MyNamespace = MyNamespace || {};
MyNamespace.Page = function() {};
MyNamespace.Page.prototype = {
callPage : function() {
"use strict";
$(document).on('change', 'select', function(event) {
event.preventDefault();
event.stopPropagation();
throw new Error('callPage method failed');
});
},
init : function() {
"use strict";
try {
this.callPage();
} catch(errorMessage) {
console.log('Error : ' + errorMessage);
}
}
};
当我用try / catch包装回调函数的内容时 - 它可以工作:
$(document).on('change', 'select', function(event) {
try {
event.preventDefault();
event.stopPropagation();
throw new Error('callPage method failed');
} catch(errorMessage) {
console.log('Error : ' + errorMessage);
}
});
知道如何简化这个以及它为什么会这样做?
答案 0 :(得分:3)
在第一个示例中,try/catch
保护设置事件处理程序的代码,而不是事件处理程序本身的代码。在触发事件之前,该代码不会运行,此时执行早已离开try
块。
考虑这个等效的例子:
try {
var foo = function() {
throw new Error("foo error");
}
}
catch (error) {
}
foo();
您不会指望调用foo
导致的错误只是因为当foo
被定义为执行时try
块内。
正如您所示,一个解决方案当然是在可能抛出的函数体内使用try/catch
。另一种解决方案是创建一个可重用的“捕获包装器”函数,可能是这样的:
function catchIfException(func, handler) {
return function() {
try {
var args = Array.prototype.slice.call(arguments);
func.apply(this, args);
}
catch (error) {
handler(error);
}
};
}
$(document).on('change', 'select',
catchIfException(
function(event) {
event.preventDefault();
event.stopPropagation();
throw new Error('callPage method failed');
},
function(error) {
console.log("error: " + error);
}
);
);