alecswan
alecswan

Reputation: 3680

First failing jQuery.ready() breaks the rest

We allow users to write code which sometimes calls jQuery.ready(function(){..}) multiple times. It seems like the first function call that throws an error prevents execution of the rest of the functions.

There was a discussion about this here with the solution wrapped jQuery.ready() in a delegate instead of wrapping the anonymous function parameter passed to jQuery.ready(..).

How can I override jQuery.ready(fn) and wrap the passed-in function parameter in a delegate which wraps it in try/catch and the passes to jQuery.ready(delegate)?

Here is an example:

<head>
  <script>
    // here is some code from third-party developer that sometimes throws an error
    jQuery.ready(function() {
      if ((new Date()).getMonth() == 0) 
        throw Error("It's January!");
    });
  </script>
</head>

<body>
  <script>
    // here is my code which should run regardless of the error in the <head> script
    jQuery.ready(function() {
      alert("I need to run even in January!");
    });
  </script>
</body>

What can I do to make code in run regardless of errors in ?

Upvotes: 10

Views: 3252

Answers (3)

FarmerBob
FarmerBob

Reputation: 1364

It's worth knowing that in JQuery 3.0 this behavior has changed, and one error in JQuery.ready() will not prevent the rest from firing.

See official documentation here:

https://github.com/jquery/jquery/issues/1823

https://jquery.com/upgrade-guide/3.0/#breaking-change-document-ready-handlers-are-now-asynchronous

Upvotes: 1

jfriend00
jfriend00

Reputation: 708206

If you need to catch your own errors, then catch them with your own try/catch:

$(document).ready(function() {
   try {
       // put your normal code here
   } catch (e) {
       // put any code you want to execute if there's an exception here
   }
});

This will allow all subsequent code to continue without pause. One might ask why you're getting errors thrown? And perhaps what you should be doing to fix that or handle that more directly?

If you want, you could do this and replace all the troublesome calls to jQuery.ready() with jQuery.safeReady():

jQuery.fn.safeReady = function(f) {
    jQuery.ready(function() {
        try {
            f();
        } catch(e) {
            // make it so you can see errors in the debugger 
            // so you would know if something was wrong
            if (window.console) {
                console.log(e);
            }
        }
    });
};

Upvotes: 7

Tadeck
Tadeck

Reputation: 137460

You can overwrite it like that:

jQuery.fn.ready = function(param){
    // do whatever you wish
};

but you should not do it. See this jsfiddle for a reason.

The example from my jsfiddle shows, that the above solution would also overwrite commonly used jQuery feature and can severely break your code.

Just rewrite your code - either by changing .ready() into .delegate() or by enclosing poorly written code within try {...} catch(...) {...} statements.

Upvotes: 1

Related Questions