91

I'm using jQuery to make an AJAX request. I want to perform different actions whether or not the HTTP status code is a 400 error or a 500 error. How can I achieve this?

$.ajax({
    type: 'POST',
    url: '/controller/action',
    data: $form.serialize(),
    success: function(data){
        alert('horray! 200 status code!');
    },
    error: function(data){
        //get the status code
        if (code == 400) {
            alert('400 status code! user error');
        }
        if (code == 500) {
            alert('500 status code! server error');
        }
    },
});

Update:

@GeorgeCummins mentioned that it "seemed odd" to work with the response body. This is the first time that I've attempted doing this sort of thing. Is my approach not a best-practice? What would you recommend? I created another StackOverflow question for this here: What response/status code should I send to an AJAX request when there is a user/form validation error?

Community
  • 1
  • 1
Andrew
  • 227,796
  • 193
  • 515
  • 708

5 Answers5

110

If you're using jQuery 1.5, then statusCode will work.

If you're using jQuery 1.4, try this:

error: function(jqXHR, textStatus, errorThrown) {
    alert(jqXHR.status);
    alert(textStatus);
    alert(errorThrown);
}

You should see the status code from the first alert.

Alex Reynolds
  • 95,983
  • 54
  • 240
  • 345
  • 1
    Oh, I see my problem. I was thinking that `data` was being passed to the error method, but it's actually `jqXHR`, `textStatus`, and `errorThrown` – Andrew Jul 14 '11 at 23:01
  • 6
    I like your answer because you mention the differences between the different versions of jQuery, which I didn't notice at first. – Andrew Jul 15 '11 at 00:12
  • 2
    I'm using your example at jQ 2.x and status is always zero (0), textStatus always 'error' and errorthrown is empty. Any ideas? What I have done: Turn of the server after the page is loaded to figure out what happen. – Codebeat Dec 23 '16 at 02:40
  • It worked for me when I got the status code 419 and I could handle the error. – disha Nov 26 '18 at 14:13
69

You should create a map of actions using the statusCode setting:

$.ajax({
  statusCode: {
    400: function() {
      alert('400 status code! user error');
    },
    500: function() {
      alert('500 status code! server error');
    }
  }
});

Reference (Scroll to: 'statusCode')

EDIT (In response to comments)

If you need to take action based on the data returned in the response body (which seems odd to me), you will need to use error: instead of statusCode:

error:function (xhr, ajaxOptions, thrownError){
    switch (xhr.status) {
        case 404:
             // Take action, referencing xhr.responseText as needed.
    }
} 
wvdz
  • 16,251
  • 4
  • 53
  • 90
George Cummins
  • 28,485
  • 8
  • 71
  • 90
  • I started down that route, but couldn't figure out how to get the data. How do you access the response body? – Andrew Jul 14 '11 at 22:56
  • @Andrew: Why do you need to access the response body? Are you expecting useful data to be returned when a 400 or 500 error occurs? – George Cummins Jul 14 '11 at 22:57
  • 2
    Yes, I'm using a status code of 400 for form validation errors. (not sure if that is appropriate or not) – Andrew Jul 14 '11 at 22:59
  • In that case, can you take the appropriate form validation action in the body of the `400: function() {`. Just remove the alert() and add the necessary code. – George Cummins Jul 14 '11 at 23:10
  • the response body contains the html of the error messages. How can I access the request body from within the `400: function() {`? – Andrew Jul 14 '11 at 23:14
  • @GeorgeCummins let us [continue this discussion in chat](http://chat.stackoverflow.com/rooms/1486/discussion-between-andrew-and-george-cummins) – Andrew Jul 14 '11 at 23:41
  • 3
    Why is it odd to tell the caller of the API what the exact problem is rather than just telling them 400. – Paul Mar 10 '17 at 11:45
15

An other solution is to use the response.status function. This will give you the http status wich is returned by the ajax call.

function checkHttpStatus(url) {     
    $.ajax({
        type: "GET",
        data: {},
        url: url,
        error: function(response) {
            alert(url + " returns a " + response.status);
        }, success() {
            alert(url + " Good link");
        }
    });
}
CodeWhisperer
  • 1,143
  • 2
  • 19
  • 39
  • 1
    this solution is best – henrry Mar 12 '21 at 09:04
  • this answer assumes that the first argument to the `error` handler is the `response` (as for the `success` handler), but this it not the case: the first argument is the `jqXHR` – am70 May 02 '23 at 08:37
10

use

   statusCode: {
    404: function() {
      alert('page not found');
    }
  }

-

$.ajax({
    type: 'POST',
    url: '/controller/action',
    data: $form.serialize(),
    success: function(data){
        alert('horray! 200 status code!');
    },
    statusCode: {
    404: function() {
      alert('page not found');
    },

    400: function() {
       alert('bad request');
   }
  }

});
genesis
  • 50,477
  • 20
  • 96
  • 125
  • 3
    how would you catch an unexpected statusCode, is there a catch-all or else handler in this version of the syntax? – joedotnot Jan 26 '19 at 01:18
0

Here you can use this too it works for me

$.ajax({
  success: function(data, textStatus, xhr) {
    console.log(xhr.status);
  },
  complete: function(xhr, textStatus) {
    console.log(xhr.status);
  } 
});