Monthly Archives: June 2009

reCaptcha with CodeIgniter Form Validation

3
Filed under Programming, Projects, Tech

If you are building a site that requires reCaptcha and you are using the CodeIgniter Form Validation libs you can tie those together nicely.

A previous version of the article included the reCaptcha lib via require_once and it was brought to my attention that using a helper would be more ‘elegant’. Frankly he was right (@jusfa) so I included how to do that below.

Download the reCaptcha library and extract into any directory (temp directory works best since we will be moving it). Then copy the file ‘recaptchalib.php’ to ’system/application/helpers/recaptcha_helper.php’ and remove the directory that you extracted the lib to (optional).

Now you can load the library with the following command.

<?php
$this->load->helper('recaptcha');
?>

If you want all methods to have access to this helper in the controller then place the command in the constructor, otherwise place it above the code that is dependent upon it.

Once your helper is setup you need to store your public and private keys that were generated from the reCaptcha site in your controller.

<?php
// store your private/public key
private $_recaptcha_private_key = 'YOUR PRIVATE KEY GOES HERE';
private $_recaptcha_public_key = 'YOUR PUBLIC KEY GOES HERE';
?>

The next step is to create a method in your controller and set the validation rules for the reCaptcha field. The rules I used are that the ‘recaptcha_response_field’ is required and you will be using the callback method named ‘recaptcha_check’. If the form validation is FALSE then you will need to call the method to generate the reCaptcha HTML and pass it to your view.

<?php
   function someAction()
    {
        $this->load->library('form_validation');
        // set validation rule for the recaptcha response
        $this->form_validation->set_rules('recaptcha_response_field', 'reCaptcha', 'required|callback_recaptcha_check');
        if ($this->form_validation->run() === FALSE)
        {
            // store the recaptcha html code for the view
            $data['recaptcha'] = recaptcha_get_html($this->_recaptcha_public_key);
            // pass the data to the view
            $this->load->view('someView', $data);
        }
        else
        {
            // party
        }
    }
?>

When the user submits the form the ‘recaptcha_response_field’ data will be passed as a parameter to your callback method ‘recaptcha_check’. Within that method you want to call the reCaptcha lib method to check the user’s answer to make sure it is correct. If it is not then you will set the form error message and return FALSE. When the user enters a correct reCaptcha response you only need to return TRUE, since no error occurred you do not need to set the error message value.

<?php
    function recaptcha_check($response)
    {
        // check to see if the recaptcha is correct
        $resp = recaptcha_check_answer (
                                        $this->_recaptcha_private_key,
                                        $this->input->ip_address(),
                                        $this->input->post('recaptcha_challenge_field'),
                                        $this->input->post('recaptcha_response_field'));
         if(!$resp->is_valid)
         {
             //reCaptcha is wrong
             $this->form_validation->set_message('recaptcha_check', 'reCaptcha was wrong.');
             return FALSE;
         }
         return TRUE;
    }
?>

Now just add in the validation for your other fields and you are done! Below is the complete script so you can see how it all fits together inside one controller.

Full Script

<?php
class Test extends Controller
{
    // store your private/public key
    private $_recaptcha_private_key = 'YOUR PRIVATE KEY GOES HERE';
    private $_recaptcha_public_key = 'YOUR PUBLIC KEY GOES HERE';

    function __construct()
    {
        parent::__construct();
        $this->load->helper('recaptcha');
    }

    function someAction()
    {
        $this->load->library('form_validation');
        // set validation rule for the recaptcha response
        $this->form_validation->set_rules('recaptcha_response_field', 'reCaptcha', 'required|callback_recaptcha_check');
        if ($this->form_validation->run() === FALSE)
        {
            // store the recaptcha html code for the view
            $data['recaptcha'] = recaptcha_get_html($this->_recaptcha_public_key);
            // pass the data to the view
            $this->load->view('someView', $data);
        }
        else
        {
            // party
        }
    }
    function recaptcha_check($response)
    {
        // check to see if the recaptcha is correct
        $resp = recaptcha_check_answer (
                                        $this->_recaptcha_private_key,
                                        $this->input->ip_address(),
                                        $this->input->post('recaptcha_challenge_field'),
                                        $this->input->post('recaptcha_response_field'));
         if(!$resp->is_valid)
         {
             //reCaptcha is wrong
             $this->form_validation->set_message('recaptcha_check', 'reCaptcha was wrong.');
             return FALSE;
         }
         return TRUE;
    }
}
?>

Links fixed

0
Filed under Servers

Turns out that wordpress was 404′ing when trying to read the posts. I cleaned up .htaccess file and copied the settings over and it seemed to fix the issue.