Running into a bit of a head scratcher passing a jQuery object to an $.ajax()
request as data. Apparently $.ajax()
processes objects into a query string using $.param()
, but $.param()
fails to properly serialize data from a multiple select element. Instead it sends only the first value.
The docs for $.param()
state:
Create a serialized representation of an array, a plain object, or a jQuery object suitable for use in a URL query string or Ajax request. In case a jQuery object is passed, it should contain input elements with name/value properties.
For this, serialize()
works just fine but $.param()
fails. Is this a bug with $.param()
or am I missing something here?
Please, I am not looking for a solution. As I have said, I can simply use serialize()
as a workaround before passing the data to $.ajax()
. The question I am asking is about the proper use of $.param()
and whether or not this is, in fact, a bug.
See example below illustrating the difference in results. Select multiple options to see the difference.
UPDATE: I added some text inputs to the demo below with the name text[]
as these should be encoded into an array the same as the multiple select. Turns out $.param()
deals with these just fine - so the problem seems to be specifically related to the select.
$('#submit').on('click', function() {
var param_query = $.param($('select, input'));
var serialize_query = $('select, input').serialize();
$('#param').html(param_query);
$('#serialize').html(serialize_query);
});
div {
margin: 10px 0;
}
#output,
i {
color: blue;
}
span {
color: #333;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<select size="5" multiple name="colors[]">
<option value="red">red</option>
<option value="gold">gold</option>
<option value="green">green</option>
<option value="black">black</option>
<option value="White">white</option>
</select><br />
<input placeholder="Enter some text here..." name="text[]" /><br />
<input placeholder="Enter some text here..." name="text[]" /><br />
<button id="submit">Submit</button>
<div><b>QUERY STRING RESULTS:</b>
<br />
<i>$.param()</i>: <span id="param"></span>
<br />
<i>serialize()</i>: <span id="serialize"></span>
</div>
It is not a bug, that's the standard behavior.
Instead of selecting the whole select
, you should inform which selected
option
s you want; $.param()
requires an array to work properly. In the snippet I inform an array as a parameter to produce the same result as serialize
does (it seems like it gets the element and transforms it into an array, because it knows a select
can be transformed into one).
As nicely informed by J Travis in the comments
param
simply does$obj.each(function(){ this.value })
andthis.value
only gets the first selection in a multiple select
For that reason $.param()
is not able to transform any HTML element into a proper array and then serialize it.
$('#submit').on('click', function() {
var selectedItemsArray = $('select').find(':selected').map(function() {
return $(this).text();
}).get();
var selectedItems = $('select').find(':selected') ;
var param_query_Array = $.param({colors: selectedItemsArray});
var param_query_Selected = $.param( selectedItems);
var serialize_query = $('select').serialize();
$('#param').html(param_query_Array);
$('#paramSelected').html(param_query_Selected);
$('#serialize').html(serialize_query);
});
div {
margin: 10px 0;
}
#output,
i {
color: blue;
}
span {
color: #333;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<select size="5" multiple name="colors[]">
<option value="red">red</option>
<option value="gold">gold</option>
<option value="green">green</option>
<option value="black">black</option>
<option value="White">white</option>
</select>
<button id="submit">Submit</button>
<div><b>QUERY STRING RESULTS:</b>
<br />
<i>$.param()</i>: <span id="param"></span>
<br />
<i>$.param($('select').find(':selected')</i>: <span id="paramSelected"></span>
<br />
<i>serialize()</i>: <span id="serialize"></span>
</div>
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