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 options 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
paramsimply does$obj.each(function(){ this.value })andthis.valueonly 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