Submit codeigniter form using jQuery AJAX

Codeigniter provides a form helper library which is excellent for handling forms and validations, but when it comes to handling forms using jQuery ajax, there is no native support. However, you can use $this->input->is_ajax_request() to detect if the submitted request is AJAX.

As part of this tutorial, below are the main points we will be covering:

  1. Create a controller method which will show the form and accept the submitted data through POST.
  2. Create a normal HTML form in the view and then add code to submit it using ajax.
  3. Submit form data by serializing with jQuery serializeArray() and handle submitted data in the controller. Display it for demo purposes.
  4. Refresh the page after submitting the form successfully with a time delay of 2 seconds.

Create a controller method to accept AJAX data through POST

Create a controller method Ajax_form as below to accept ajax data through POST. For our tutorial, we have created it under demo folder in controller(demo/Ajax_form). See the inline comments for explanation of the code.

demo/Ajax_form
<?php

if (!defined('BASEPATH'))
    exit('No direct script access allowed');
/* 
 * Tutorial by technology-central.org
 */
class Ajax_form extends CI_Controller {
        public function __construct()
        {
                parent::__construct();
                // Put your own constructor code here
                // load your model here if any DB operations through model
                //$this->load->model('demo/form_model','fm');
        }
        public function index()
        {
                // Index page which gets loaded when someone visits /demo/ajax_form
                //Load CI form and url helpers needed later
                $this->load->helper(array('form','url'));
                // Load CI form_validation library    
                $this->load->library('form_validation');
                //Below line sets validation rules. 'name' has been made required. The rules are automatically
                // enforced by CI form validation library.
                $this->form_validation->set_rules('name', 'Name', 'required');

                if (!($this->input->post(NULL,TRUE)) )
                {
                    // This loop is executed when the form loads initially and no data has been submitted.
                    // Load the form to be seen and submitted by user. This form is created at demo/form_view
                    // under view folder. If form is located at any other place , change the below accordingly.
                        $this->load->view('demo/form_view');
                }
                elseif ($this->input->post(NULL,TRUE) AND $this->form_validation->run() === FALSE)
                {
                        // '$this->input->post(NULL,TRUE)' ensures that data has been submitted through POST method
                        // and CI returns all the data through XSS filtering.
                        // '$this->form_validation->run() === FALSE' checks if the form has passed all the validation rules
                        // or not. FALSE is returned when any validation fails.
                        // this loop will execute only when data has been submitted through POST and form validations failed.
                        $form_ret['error'] = 'Y' ; // Setting error indicator to 'Y' 
                        $form_ret['message'] = validation_errors() ; // Return validation error messages back to form
                        die(json_encode($form_ret)); // JSON encode all the values and return them back to calling form. die() ensures that control returns back and no further code is executed.
                        
                }                
                else
                {
                        // This loop is executed when the form has been submitted and there are no form validation errors
                        // Values from the POST can be extracted as below and used either for display or stored in database.
                        //var_dump($this->input->post(NULL,TRUE)) ; // Use this if you want to check the array submitted through POST.
                        $name = $this->input->post(NULL,TRUE)['name'] ;
                        $dob = $this->input->post(NULL,TRUE)['dob'] ;
                        $email = $this->input->post(NULL,TRUE)['email'] ;
                        $form_ret['error'] = 'N' ; // Set error indicator to 'N'
                        // setting some success message and passing back the submitted values to be displayed.
                        // In a real application, you may want to store the submitted values in database or process
                        // them as per your application logic.
                        $form_ret['message'] = "Successfully submitted. Name: $name , date of birth: $dob, Email: $email" ;
                        die(json_encode($form_ret)); // JSON encode the return values and pass the control back. 
                }
        }
}

Create View file

Create a view file form_view. For our tutorial, we created it under demo folder in view, create it as per your needs. Inline comments have been added explaining the code and logic.

demo/form_view
<?php

if (!defined('BASEPATH'))
    exit('No direct script access allowed');
?>
<html>
<head>
    <title>AJAX Demo on technology-central.org</title>
    <!-- Jquery library which will be used for Jquery AJAX tutorial -->
    <script src="https://ajax.googleapis.com/ajax/libs/jquery/1.12.0/jquery.min.js"></script>
    <!-- comments have been added for explanation, you may want to remove them if you copy this code, since the
         comments in html will be visible publicly. -->
</head>
<body>
<!-- You can display any form validation errors here. Since we are using Jquery AJAX, we will not use and you can remove it-->
<?php echo validation_errors(); ?>
<!-- Open the form with CI form_open(). One benefit of using this is CSRF tokens are automatically included in 
     the form when you use form_open. Change 'demo/ajax_form' below to the controller method you are submitting
    this form to. However, since we are going to use AJAX to submit form, we'll specify URL parameter there. 
    Notice the 'demoform' ID assigned to form which will be used later in Jquery. Change as per your needs.-->
<?php echo form_open('demo/ajax_form','id="demoform"'); ?>

<h5>Name</h5>
<input type="text" name="name" value="" size="30" />

<h5>Date of Birth</h5>
<input type="text" name="dob" value="" size="20" />

<h5>Email Address</h5>
<input type="text" name="email" value="" size="80" />

<div><input type="submit" value="Submit" /></div>

<?php echo form_close(); ?>

<!-- Below Div area will be used to display success and error messages-->
<div id="form_msg"></div>
<!-- Consider including a link back to http://technology-central.org/ if you found this useful.-->
<div> Tutorial by:  <a href="http://technology-central.org/"> http://technology-central.org/ </a></div>
<script>
    // start javascript here
    // Catch the submit event of #demoform (demoform is the ID of the above form) through Jquery. 
    // Make sure Jquery is loaded either locally or through a CDN.
    $( "#demoform" ).submit(function( event ) {
        // event.preventDefault() will make sure that the default form is not submitted normally when 
        // you click the submit button. This is important
        event.preventDefault();
        
    // Start jquery ajax below    
    $.ajax({
        method: "POST",
        // site_url() returns the url including/excluding index.php. This is recommended.
        // uri_string() returns the current URI where the form is loaded. If the form needs to be submitted to 
        // a different controller menthod, change this value accordingly.
        url: "<?php echo site_url().'/' . uri_string();?>",
        // $("#demoform").serializeArray() serializes all the values in the form into an array for submissing.
        // This is very important for submitting the form correcly.
        // If you are extracting the form values individually and submitting them, make sure CSRF token name and hash
        // values are also passed, otherwise you will face a 403 Forbidden error while submitting the form,
        // in case you have CSRF protection enabled. Here, since CSRF token name and token hash are automatically created
        // as hidden fields with CI form_open() method, they are also passed in the serialized array and things 
        // work automatically.
        data: $("#demoform").serializeArray()
    })
        .done(function( return_data ) {
            // This loop is executed when ajax call is done and control is returned back. 
            // Display return_data like below if you want to examine raw data returned in case of any issues.
            //alert( "Data returned: " + return_data );
            try {
                // TRY block when there is no exception. Since data was JSON encoded within controller,
                // we are using jquery $.parseJSON method to parse the emncoded data.
                ret = $.parseJSON(return_data);
                if(ret.error === 'Y' ) { 
                    // if error indicator was set, append the return message to form_message div element.
                $("#form_msg").empty().append(ret.message);
              }
              else {
                  // if no error, display success message. You may want to perform other business business logic as
                  // per you application here.
                  $("#form_msg").empty().append(ret.message);
                  $( "#form_msg" ).append( '<p style="color:green"> Refreshing the page in 2 seconds.. </p>' );
                  // Since the form was submitted using AJAX, you will want to refresh the page since the CSRF 
                  // token hash may be invalidated. Also, the form values will be reset with page refresh.
                    function redirect_delay() {
                        // location.reload(true) will load the same page again. TRUE will make sure page is
                        // reloaded from server and not from browser cache.
                        location.reload(true);
                    }
                    // This will wait for the specified time and execute redirect_delay() function. In the below case,
                    // we are waiting 2000 milliseconds (2 seconds) before refreshing the page.
                    setTimeout(redirect_delay, 2000);
              }
            }
            catch(e) {
               // Catch any exceptions here and handle as needed. Use console.log(e) to write the exception to 
               // browser console, only in the development environment.
               //console.log(e) ;
               // return false will ensure code execution is stopped here. Make sure it is in lower case
               // i.e. 'false' and not 'FALSE' .
               return false ; 
              }          
    });
});
</script>    
</body>
</html>

Test the form

Go to controller method demo/ajax_form on your website (e.g. if your website is example.com , go to example.com/demo/ajax_form). If you have used correct URLs for controller and views, you should have a working AJAX form now. Play around and see how it works.

Following the tutorial, you can create complex forms and use submitted values as per your needs.

CSRF special cases

However, if you are not using form_open() method or submitting form values individually and your application is having CSRF protection enabled, you will need to modify the ajax code as below. If you do not have CSRF protection enabled, consider enabling it for security reasons , follow the tutorial on how to set up csrf protection on codeigniter.

data: { '<?php echo $this->security->get_csrf_token_name(); ?>':'<?php echo $this->security->get_csrf_hash(); ?>',data }

here, data is the variable you are submitting normally and

'<?php echo $this->security->get_csrf_token_name(); ?>':'<?php echo $this->security->get_csrf_hash(); ?>'

would contain CSRF token name and token value.

Value of variable data would be available in the controller using $this->input->post()['data'] . CSRF token name and hash would be used by CI security class automatically and you do not need to write any code for that.

If you face any issues setting it up, let me know using the comments section.

Common issues

  • HTTP 403 Forbidden issue: This will happen when the CSRF token name and hash values are not being passed to controller correctly. Another reason is when the page is left idle for long time, csrf token may get invalidated. Refresh the page and check the variable dump for values being passed.
  • Form being submitted normally without using AJAX : This will happen when the event.preventDefault() has not been specified or if there is any error in the javascript/ jquery syntax. Turn on the browser console and look for any errors during initial page load or submission.

Other questions which this post should be able to answer

  1. How to submit codeigniter form using jQuery ajax method?
  2. How to use jQuery serializeArray() method to submit data using AJAX?
  3. How to refresh a page with delay using JavaScript / jQuery?
  4. How to submit a codeigniter form with CSRF token name and hash using AJAX?
  5. How to return false in JavaScript or stop code execution in JavaScript? (Answer: use “return false ; ” )

References:

 

Leave a Reply

Technology Central © 2014 - 2017 | Privacy Policy | Website Terms & Conditions