Created
January 6, 2012 14:20
-
-
Save jaspertandy/1570808 to your computer and use it in GitHub Desktop.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<?php | |
/** | |
* Simple XSRF protection. | |
*/ | |
class Session_Key { | |
/** | |
* constants, USER and FORM are used to identify session data, USER, FORM and FORMID are used as | |
* input names so validation is encapsulated easily | |
*/ | |
const USER = 'SESSIONKEY_USERKEY'; | |
const FORM = 'SESSIONKEY_FORMKEY'; | |
const FORMID = 'SESSIONKEY_FORMID'; | |
/** | |
* easier access to stuff stored in session. Can't be bothered writing $_SESSION all the time | |
*/ | |
protected $user; | |
protected $form; | |
/** | |
* the currently-generated form key and id. Really, this class should be called every time | |
* you want a new one, but reloads are handled as best as possible internally | |
*/ | |
protected $current_form_key = ''; | |
protected $current_form_id = ''; | |
public function __construct(){ | |
if ( !array_key_exists( self::USER , $_SESSION ) ) { | |
$this->user_key(); | |
$_SESSION[ self::FORM ] = array(); | |
} | |
$this->reload(); | |
} | |
/** | |
* As we only ever modify the data in the session to ensure persistence, this function is | |
* needed to make sure that the class internals are always up-to-date | |
* | |
* call every time a modification is made to the session data | |
*/ | |
protected function reload(){ | |
$this->user = $_SESSION[ self::USER ]; | |
$this->form = $_SESSION[ self::FORM ]; | |
} | |
/** | |
* Generate a new form key and id | |
*/ | |
protected function restart(){ | |
$this->current_form_key = $this->generate_key(); | |
$this->current_form_id = $this->generate_key(); | |
} | |
/** | |
* generate a random string to use as a key | |
*/ | |
protected function generate_key(){ | |
return sha1( microtime(true) . mt_rand() . uniqid() ); | |
} | |
/** | |
* generate a new user key. One one-time per session is needed really | |
*/ | |
public function user_key(){ | |
$_SESSION[ self::USER ] = $this->generate_key(); | |
} | |
/** | |
* create a new form key | |
*/ | |
public function form_key(){ | |
$this->restart(); | |
$_SESSION[ self::FORM ][ $this->current_form_id ] = $this->current_form_key; | |
$this->reload(); | |
return $key; | |
} | |
/** | |
* return the HTML needed to validate with data generated by this class | |
*/ | |
public function form_fields(){ | |
$this->form_key(); | |
return '<input type="hidden" name="'.self::USER.'" value="'. $this->user .'"/><input type="hidden" name="'.self::FORM.'" value="'. $this->current_form_key .'"/><input type="hidden" name="'.self::FORMID.'" value="'. $this->current_form_id .'"/>'; | |
} | |
/** | |
* make sure that the form sent was sent by this class | |
*/ | |
public function validate( Validation $obj , $field ){ | |
$this->reload(); | |
if ( $obj->{ self::USER } !== $this->user ) return false; // User session key mismatch | |
if ( $obj->{ self::FORM } !== $this->form[ $obj->{ self::FORMID } ] ) return false; // Form key mismatch | |
unset( $_SESSION[ self::FORM ][ $obj->{ self::FORMID } ] ); | |
$this->reload(); | |
return true; | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment