Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Best practices for receiving server exception messages on ajax request

The essence of my question is this: If I issue a $.ajax request to my server for server-side validation -- how should I expect to handle the validation response? I see myself as having two options:

//  Server handled error:
$.ajax({
   url: 'controller/action',
   data: {},
   success: function(response){
       console.log("Error:", response.error);
   }
}

//  Server unhandled error:
$.ajax({
   url: 'controller/action',
   data: {},
   success: function(){
   },
   error: function(error){
       console.log("Error:", error);
   }
}

The former example assumes that my server's controller has a try/catch which consumes any server-side exceptions. It then takes any exceptions and returns them as part of the json success object. The latter allows the server's exception to bubble up through and be caught in the ajax error handler.

Personally, I thought I preferred the latter. However, I just encountered an issue with remoting -- if our server's security settings aren't relaxed then the error message gets hidden as a 'Runtime Error' and reading the error information from the ajax's onerror event handler becomes impossible.

I would like to avoid that issue, I need to always be able to read my errors, but it seems really wrong to have my ajax request always return successful.

How is this normally handled?

[HttpPost, AjaxOnly]
public ActionResult ChangePassword(ChangePasswordDialogModel model)
{
    string error = string.Empty;

    if (model.NewPassword == model.NewPasswordConfirm)
    {
        using (var service = new SecurityServicesSoapClient())
        {
            error = service.ChangePassword(SessionManager.Default.User.UserName, model.OldPassword,
                                           model.NewPassword);
        }
    }
    else
    {
        error = "New Password and Confirm do not match. Please re-enter";
    }

    if (!string.IsNullOrEmpty(error))
        throw new Exception(error);

    return Json(new
        {
            success = true
        });
}

This versus setting success to false and setting an error property to the error message.

like image 343
Sean Anderson Avatar asked Oct 04 '22 12:10

Sean Anderson


1 Answers

I do something quite similar in my system. Success always returns data like:

$data['success'] = array(/* your data to be served back to the page */); //PHP

whereas errors are always done like:

$data['errors'] = array(/* your error data */); //PHP

You can set flags to look for exception codes in your controller catch() statements to filter types of error messages. In your JS code you just do:

// JS
$.ajax({success:function(data) {
    if (data.success !== undefined) {}
    else if (data.errors !== undefined) {}
}});

You can get crazier and add them as global AJAX handlers as well by adding this code to a $(document).ajaxComplete(); callback.

You can and should have a separate handler for the ajax error callback, because that can include situations that your controller code has no control over (404 errors, server unreachable, etc).

like image 81
Derek Avatar answered Oct 07 '22 17:10

Derek