One token vs. multiple tokens to prevent CSRF attacks One token vs. multiple tokens to prevent CSRF attacks codeigniter codeigniter

One token vs. multiple tokens to prevent CSRF attacks


I scanned your post and don't see a reason why not to use the base codeigniter CSRF protection? It seems you are reinventing the wheel and creating problems that don't exist within its standard implementation.

Not to mention you are violating DRY principles by trying to print your tokens to every form. Any reason why not to keep it simple?

Codeigniter has build in CSRF protection that can be enabled in /application/config/config.php

$config['csrf_protection'] = TRUE;$config['csrf_token_name'] = 'csrf_token_name';$config['csrf_cookie_name'] = 'csrf_cookie_name';$config['csrf_expire'] = 7200;


To solve this problem, you could create a token string with a unique key and store the pairs of keys/tokens in the session (as userdata in CodeIgniter).

Considering this scenario, You'll need these steps:

  1. Creating a unique token key.
  2. Creating a token string.
  3. Storing the key/token pair in the session (userdata).
  4. Creating 2 hidden <input> elements for CSRF key and token.
  5. Validating the posted key/token by checking the existence of key/token in the session.

Getting to work:

$csrf_key   = "TOKEN_" . mt_rand(0, mt_getrandmax());$csrf_token = hash("sha512", mt_rand(0, mt_getrandmax()));// Store the key/token pair in session$this->session->set_userdata($csrf_key, $csrf_token);

Adding hidden inputs:

<form action="path/to/handler/page" method="post">    <!-- form input elements -->    <input type="hidden" name="csrf_key" value="<?php echo $csrf_key; ?>">    <input type="hidden" name="csrf_token" value="<?php echo $this->session->userdata($csrf_key); ?>"></form>

Validating the posted key/token:

if (count($_POST)) {    if (! isset($_POST['csrf_key']) or ! isset($_POST['csrf_token'])) {        die('No CSRF token found, invalid request.');         }    $key   = $this->input->post('csrf_key');    $token = $this->input->post('csrf_token');    if ($token !== $this->session->userdata($key)) {                        die('Invalid CSRF token, access denied.');    }}