jQuery's AJAX .fail()
is a nice error handler that handles "404 Not Found" errors and such, but how can we call it deliberately from inside .done()
to handle general error cases, for example when data provided by user is incorrect?
JavaScript provides error-handling mechanism to catch runtime errors using try-catch-finally block, similar to other languages like Java or C#. try: wrap suspicious code that may throw an error in try block. catch: write code to do something in catch block when an error occurs.
The best way to bubble that error from the server side (using php) to the client side is to send a header through the Ajax request somewhere in the 400's (which is always associated with errors). Once the Ajax request receives this it will trigger your error function.
In JavaScript, all exceptions are simply objects. While the majority of exceptions are implementations of the global Error class, any old object can be thrown. With this in mind, there are two ways to throw an exception: directly via an Error object, and through a custom object.
To return errors from functions as promises, there are generally two ways to produce rejected promises: The reject function of your Promise library. Throwing an exception in a then callback or returning a rejected promise from it will reject the resulting promise.
You can use a common function that's called on error in each case.
$.ajax( 'url' )
.done( function( data, textStatus, jqXHR ) {
if( data == 'Invalid' ) {
ajaxError( jqXHR, "usererror" );
}
})
.fail( ajaxError );
function ajaxError( jqXHR, textStatus, errorThrown ) {
console.log( 'Ajax error: ' + textStatus );
}
@Juhana's code will be good for most eventualities.
If, however, errors might arise that cannot be reliably predicted by inspection of data
alone, then consider this variant :
$.ajax( 'url' ).done( function( data, textStatus, jqXHR ) {
try {
var dataLooksGood = ......;//(boolean) Test data for predictable data errors here
if( !dataLooksGood ) throw( new Error("data invalid"); )
//Handle data here.
//Any naturally-ocurring errors or further manually-thrown errors will be caught below.
}
catch(err) {
ajaxError( jqXHR, "AJAX successful but: " + err.message );
}
}).fail( ajaxError ).always(function() {
//Here do whatever is necessary after success or error
});
function ajaxError( jqXHR, textStatus, errorThrown ) {
console.log( 'AJAX error: ' + textStatus );
}
By catching errors, the always
handler will be allowed to fire even if an unpredicted error occcurs. Thus you could better guarantee that a "loading..." message or spinner graphic was killed regardless of an error having occurred.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With