【问题标题】:jQuery method throw new Error - not catched by the outside try / catch blockjQuery 方法抛出新错误 - 未被外部 try/catch 块捕获
【发布时间】:2014-07-26 03:57:55
【问题描述】:

我开始向我的 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);

    }

});

知道如何简化这一点以及为什么会这样吗?

【问题讨论】:

    标签: javascript jquery error-handling javascript-objects


    【解决方案1】:

    在第一个示例中,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);
            }
        );
    );
    

    【讨论】:

    • 我明白了。我来自 PHP 背景,它同步处理所有内容 - 因此我对这个主题有误解。感谢您的澄清-您认为通过在 try / catch 块中创建执行回调函数的错误处理函数是一个不错的选择吗?我的意思是说 function tryCatch(callback) { try { callback(); } 捕捉(错误){ console.log(错误); } ?
    • @SpencerMark:这取决于。如果错误处理程序将被大量重用,这可能是一个好主意,否则编写 try/catch 内联会更简单,也不会更糟。请注意,提议的tryCatch 需要更多参与(它应该保留this 并转发任何参数),请参阅上面的catchIfException
    • 感谢 Jon - 非常感谢您的帮助。我是否必须单独使用处理程序,还是可以直接从 catchIfException() 的 catch 语句中将错误记录到控制台?或者也许做一个条件检查它是否被指定,如果是,则使用它 - 否则只需记录?
    • @SpencerMark:我真的不能说,因为这一切都取决于你的具体情况。
    猜你喜欢
    • 2012-06-06
    • 2014-03-04
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2019-05-19
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多