Ajax Content Type Handling in jQuery

July 09, 2010

Before jQuery 1.4, you had to specify the dataType in all of the types of ajax requests.

$.get(url, data, function, "html/json/xml..");
$.post(url, data, function, "html/json/xml..");
$.ajax({

dataType: "html/json/xml.."
});

Now, you can have the server respond with the mime type like application/json and jQuery will automatically switch the dataType for you! This makes more sense because the server is the one sending the response, jQuery is only handling it.

There is only one problem with this. The server may respond with different mime types based on what it is trying to do.

For instance, in many server side frameworks (ruby on rails, grails, cakephp, symphony, code igniter, etc) they all have form helper plugins that render form errors for based on server side logic. So if you request a form with ajax and attempt to submit it with errors, it will respond back with the HTML form including all errors.

This is a pretty easy scenario to handle.

$.post("/widgets", widgetForm.serialize(), function(response){
widgetForm.replaceWith(response);
});

But what if you want the server to respond with JSON on success? It is difficult in the above example to branch. So, what I did was look into jQuery’s core to see how to read the response header. Then we can branch our response logic accordingly.

In order to do this, we’ll have to use the ajax method, because the success function sends back the XMLHttpRequest object that we’ll use to read the content type.

$.ajax({
type: "POST",
url: "/widgets",
data: widgetForm.serialize(),
success: function(response, status, xhr){
var ct = xhr.getResponseHeader("content-type") || "";
if (ct.indexOf(html) > -1) {
widgetForm.replaceWith(response);
}
if (ct.indexOf(json) > -1) {
// handle json here
}
}
});

This is perfect for handling different mime types sent from the server! =)

9 comments

#1. Alberto on July 09, 2010

Hello Marc,

I have done a similar implementation in a mashup application.

That’s great.
Congratulation

#2. AD7six on July 09, 2010

You might want to take advantage of the way jquery reads and uses the content type meaning (e.g.) :

success:function(response) {
if (typeof(response) === "object") {
// It’s json

return;
}
// It’s a html snippet
widgetForm.replaceWith(response);

Obviously this only handles two cases, json and html but I suspect that’s enough for most users :)

#3. Jeroen on July 09, 2010

But beware of IE7 that doesn’t understand any of these headers, IE7 only understands Content-type: text/plain, for json data.

#4. Marc Grabanski on July 09, 2010

Jeroen: I was wondering about that, thanks for the tip. I’ll probably switch to using AD7Six’s solution.

#5. Valentino on July 10, 2010

A better solution may be to avoid html at all. Use only json, and encapsulate html partials inside json variables.

Using json+html partials give you more flexibility.

For instance, you may need to display a lightbox if a form doesn’t validate. Using json you can provide the updated html for the form and an array of validation errors in the same ajax call.

#6. Marc Grabanski on July 11, 2010

Valentino, I agree with you that sending HTML output inside JSON is more flexible and almost always the optimal solution! However, for many server side frameworks this isn’t the default behavior so it takes hacks to get around.

#7. Rodrigo Web on September 06, 2010

I agree with Valentino. JSON is your friend. Why look for ways around using json instead of looking for efficient ways of incorporating it within the logic of your code?!

#8. Biran on October 25, 2010

This post solved my datatype problem in my program.

#9. tom.christopher on August 23, 2011

I purchased the video but I’m still being prompted for the $25. What did I purchase?

Leave a comment

Comment in textile images by gravatar