The code quest Coding for good

How to sumbit form using jQuery and ajax request

The problem

Passive data collection from your users is every day more and more common in modern applications, but you still require to get user information proactively. Normally, sending the whole form data as a key-value map use to be enough, but sometimes you need to build more complex data structures before submiting the form. And here is when JSON came to your resque. Furthermore, multidevice applications use a SOA arquitecture approach where JSON has became an standard to share data between the UI and the business layers. Then, we show 4 different ways to prepare data for your server request using the jQuery serialization feature.

Technologies

Solution

Building the UI

Guess that we want to send user registration data to backend service. The form data structure is the following:

User:
  • First name
  • Last name
  • Address
    • Street
    • City
    • Zip Code
  • Email
    • [0]
    • [1]
    • ...


We use bootstrap to build our sig up form.

Click here to see the entire html code

Creating email array fields dynamically

1 - The entry form data must allow to add multiple emails per user. So, we create the field for the first email, and we'll also let the user add new fields if necessary.

<div class="control-group" id="emails">
    <div class="controls">
        <div class="entry input-group form-group">
            <span class="input-group-addon">@</span>
            <input class="form-control" name="emails[0]" placeholder="add email" type="text">
            <span class="input-group-btn">
                <button class="btn btn-success btn-add" type="button">
                    <span class="glyphicon glyphicon-plus"></span>
                </button>
            </span>
        </div>
    </div>
</div>
<small>Press <span class="glyphicon glyphicon-plus gs"></span> to add another email :)</small>

2 - Javascript code to add a new email entry field:

$(document).on('click', '.btn-add', function(event) {
    event.preventDefault();
    var controlForm = $('.controls');
    var currentEntry = $(this).parents('.entry:first');
    var newEntry = $(currentEntry.clone()).appendTo(controlForm);
    newEntry.find('input').val('');
    controlForm.find('.entry:not(:last) .btn-add')
        .removeClass('btn-add').addClass('btn-remove')
        .removeClass('btn-success').addClass('btn-danger')
        .html('<span class="glyphicon glyphicon-minus"></span>');

    var inputs = $('.controls .form-control');
    $.each(inputs, function(index, item) {
        item.name = 'emails[' + index + ']';
    });
});

3 - And javascript code to remove an entry field:

$(document).on('click', '.btn-remove', function(event) {
    event.preventDefault();
    $(this).parents('.entry:first').remove();
    var inputs = $('.controls .form-control');
    $.each(inputs, function(index, item) {
        item.name = 'emails[' + index + ']';
    });
}); 

Mocking the response from server

You have to include jquery-mockjax library to fake responses from the server (you can read more about this library here: how to mock ajax responses)

<form id="ajaxForm" class="form-vertical" role="form" autocomplete="off" method="POST" action="/ajaxRequest/">
$.mockjax({
    url: '/ajaxRequest/plainjson/',
    type: 'POST',
    contentType: 'text/json',
    responseTime: 0,
    response: function(settings) {
      var data = settings.data;
      this.responseText = data;
    }
});  

Form data JSON serialization

Here we show 4 different ways to serialize form data for submission. We go from the most simple type provided by jquery till a custom processing to build a readable json structure (object oriented)

1 - jquery.serialize(). This method creates a text string in standard URL-encoded notacion.

Main code:

var form = $('#ajaxForm');
var data = $(form).serialize();

Result:

firstname = firsname_value & lastname = lastname_value & address[street] = street_value & address[city] = city_value & address[zip] = zip_value & emails[0] = email0_value & emails[1] = email1_value

2 - jquery.serializeArray(). Creates a JS array of objects ready to be encoded as a JSON string.

Main code:

var form = $('#ajaxForm');
var arrayData = $(form).serializeArray();
var data = JSON.stringify(arrayData);

Result:

[{"name":"firstname", "value":"firstname_value"},{"name":"lastname", "value":"lastname_value"}, {"name":"address[street]","value":"street_value"},{"name":"address[city]","value":"city_value"}, {"name":"address[zip]","value":"zip_value"},{"name":"emails[0]","value":"email0_value"}, {"name":"emails[1]","value":"email1_value"}]

3 - Prettify jqyery.serializeArray() function.

Main code:

var form = $('#ajaxForm');
var jsonData = {};
$.each($(form).serializeArray(), function() {
    jsonData[this.name] = this.value;
});
var data = JSON.stringify(jsonData);

Result:

[{"firstname":"firstname_value","lastname":"lastname_value","address[street]":"street","address[city]":"street_value","address[zip]":"zip_value","emails[0]":"email0_value","emails[1]":"email1_value"}]

4 - Custom serialization taking care about arrays fields and group fields.

Code:

Result:

{"firstname":"firstname_value","lastname":"lastname_value","address":{"street":"street_value","city":"city_value","zip":"zip_value"},"emails":["email0_value", "email1_value"]}

Resources:

  • Test this code here
  • Download source here