Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Why does this jQuery AJAX PUT work in Chrome but not FF

In Chrome this does an HTTP PUT just like it should, but in FireFox 21 it doesn't. There are no errors in the javascript console or in the backend.

Here is the HTML:

<div id="createTeamModal" class="small reveal-modal">
        <form id="createTeamForm">
            <div class="row"><p id="teamFlavorText" class="lead">Building a new team</p></div>
            <div class="row">
                <div class="small-4 large-4 columns"><label>Team Name:</label></div>
                <div class="small-6 large-6 columns"><input name="teamName" id="teamName" type="text" size="20"/></div>
            </div>
            <div class="row"><p class="lead">Does this team work for a business?</p></div>
            <div class="row">
                <div class="small-4 large-4 columns"><label>Business Size:</label></div>
                <div class="small-6 large-6 columns">
                    <select id="businessSizeSelect" name="businessSizeSelect">
                    <option value="1">Nope, I work alone</option><option value="2">2 to 49</option><option value="3">50 to 99</option><option value="4">100 to 999</option><option value="5">1,000+</option>
                    </select>
                </div>
            </div>
            <div id="businessLocationDiv" class="row" style="display: none; margin-top: 20px;">
                <div class="small-4 large-4 columns"><label>Business Location:</label></div>
                <div class="small-6 large-6 columns">
                    <select id="businessLocationSelect" name="businessLocationSelect">
                    </select>
                </div>
            </div>
            <div id="businessTypeDiv" class="row" style="display: none; margin-top: 20px;">
                <div class="small-4 large-4 columns"><label>Industry:</label></div>
                <div class="small-6 large-6 columns">
                    <select id="businessTypeSelect" name="businessTypeSelect">                      
                    </select>
                </div>
            </div>
            <div class="row" style="margin-top: 20px;">
                <div class="large-offset-10 small-1 large-1 columns">
                    <button id="createTeamButton" class="small button">Create</button>
                </div>
            </div>
        </form>
        <a class="close-reveal-modal">&#215;</a>
    </div>

And here is the jQuery:

$("#createTeamButton").click(function () {
    var teamObject = new Team();
    teamObject.description = $("#teamName").val();
    teamObject.businessSize = $("#businessSizeSelect").val();
    teamObject.businessType = $("#businessTypeSelect").val();
    teamObject.businessLocation = $("#businessLocationSelect").val();

    $.ajax({
        type: "PUT",
        url: "/ajax/rest/team",
        dataType: "json",
        data: JSON.stringify(teamObject),
        success: function () {
            // Reload the team select box
            loadTeamSelectBox();

            // Pop up the site create modal
            $('#createSiteModal').foundation('reveal', 'open');
        },
        error: ajaxErrorHandler
    });
});

I have observed them in Fiddler, and the difference between working (Chrome) and not working (Firefox) is that the HTTP PUT fires in Chrome and does not fire in Firefox.

Now, I know that jQuery.ajax PUT is not guaranteed in all browsers.

I have read

  • Are the PUT, DELETE, HEAD, etc methods available in most web browsers?
  • http://annevankesteren.nl/2007/10/http-method-support

These sites reaffirm that PUT may not work in all browsers, but should work in FF.

Finally, I hit the following with FF21 and PUT works

  • http://www.mnot.net/javascript/xmlhttprequest/

I could certainly engineer around this, but it seems to me this should work. I would rather not jerry-rig something, but rather get jQuery's .ajax to work properly.

Other Details: * jQuery version 2.0.0 * Backend is Spring3

[ Edit to add the HTML ]

like image 438
Lurk21 Avatar asked May 23 '13 03:05

Lurk21


People also ask

Does Google Chrome support Ajax?

Ajax is supported in all modern browsers. We suggest using the following browsers: Google Chrome. Mozilla Firefox.

What happens if an Ajax request made using jQuery fails?

version added: 1.0. Whenever an Ajax request completes with an error, jQuery triggers the ajaxError event. Any and all handlers that have been registered with the . ajaxError() method are executed at this time.

Can Ajax be used with jQuery?

jQuery provides several methods for AJAX functionality. With the jQuery AJAX methods, you can request text, HTML, XML, or JSON from a remote server using both HTTP Get and HTTP Post - And you can load the external data directly into the selected HTML elements of your web page!

Is Ajax better than jQuery?

While JQuery is a library for better client-side web page development, AJAX is a technique of doing XMLHttpRequest to the server from the web page and sending/retrieving data used on a web page. AJAX can change data without reloading the web page. In other words, it implements partial server requests.


3 Answers

I can't re produce your claim on firefox 21.0 on windows, when I go to google.com and press f12 (firebug) then run the following code:

var s = document.createElement("script");
s.src="http://code.jquery.com/jquery-1.9.1.js";
document.body.appendChild(s);
//allow some time to load and then run this
 $.ajax({
  type: "PUT",
  url: "/search",
  dataType: "json",
  data: JSON.stringify({hi:"there"}),
  success: function (data) {
    console.log(data);
  },
  error: function(e) { 
    console.log(e); 
  }
  });

I get response 405 method not allowed but more importantly; when opening up the details of the connection in the console I can see PUT, not post.

When I go to http://jqueryui.com/autocomplete/#remote and run the code (without having to include JQuery) using url:"/resources/demos/autocomplete/search.php" the xml ends successful and firebug shows PUT request.

I don't know a site where I can test if server side code detects the PUT request (google refuses POST as well so it could be a POST) but from the looks of Firebug reporting it is sending a PUT request.

[UPDATE]

I can confirm that on Firefox 21.0 the code above is 100% sure making a PUT request. Just tested it with a .net app and both Chrome 27.0.1453.94 FF set a PUT request.

like image 77
HMR Avatar answered Oct 13 '22 13:10

HMR


I think you might be missing something else - this jsFiddle does a PUT request on newest Chrome and Firefox 21 :

http://jsfiddle.net/QKkQg/

     var teamObject = new Object();
    teamObject.description = $("#teamName").val();
    teamObject.businessSize = $("#businessSizeSelect").val();
    teamObject.businessType = $("#businessTypeSelect").val();
    teamObject.businessLocation = $("#businessLocationSelect").val();

    $.ajax({
        type: "PUT",
        url: "/ajax/rest/team",
        dataType: "json",
        data: JSON.stringify(teamObject),
        success: function () {
            // Reload the team select box
            loadTeamSelectBox();

            // Pop up the site create modal
            $('#createSiteModal').foundation('reveal', 'open');
        },
        error: function() { }
    });
like image 1
kobigurk Avatar answered Oct 13 '22 15:10

kobigurk


You are not specifying what type of content you are sending to the server. I had a similar problem where the server didn't even try to read the data from the query as it did not know what the provided format was, so it just ignored it.

When specifying a dataType to a jQuery request, you are merely telling jQuery what is the expected format that the server should reply you with. To tell the server what data format you are sending, you must provide a contentType :

$.ajax({
    type: "PUT",
    url: "/ajax/rest/team",
    dataType: "json",
    contentType: "application/json",
    data: JSON.stringify(teamObject)
}).done(function() {
    // Reload the team select box
    loadTeamSelectBox();

    // Pop up the site create modal
    $('#createSiteModal').foundation('reveal', 'open');

}).fail(ajaxErrorHandler);

Backbone.js has a nice RESTful API that you can use as reference.

like image 1
Yanick Rochon Avatar answered Oct 13 '22 14:10

Yanick Rochon