php security development adds random string validation to prevent forgery of cross site requests

  • 2020-05-30 19:41:06
  • OfStack

yahoo's approach to faking cross-site requests is to add a random string called.crumb to the form; facebook has a similar solution, often with post_form_id and fb_dtsg in its forms.

A common and inexpensive precaution is to add a random and frequently changing string to all forms that might involve user writes, and then check for that string while the form is being processed. If this random string is associated with the current user's identity, it can be cumbersome for an attacker to forge a request. Now the prevention methods are basically based on this method

Random string code implementation
Let's follow this idea and copy the implementation of 1 crumb, the code is as follows:

class Crumb {  
    CONST SALT = "your-secret-salt";                                                             
    static $ttl = 7200;                                                                                            
    static public function challenge($data) {    
        return hash_hmac('md5', $data, self::SALT);    
    static public function issueCrumb($uid, $action = -1) {    
        $i = ceil(time() / self::$ttl);    
        return substr(self::challenge($i . $action . $uid), -12, 10);    
    static public function verifyCrumb($uid, $crumb, $action = -1) {    
        $i = ceil(time() / self::$ttl);                                                                               
        if(substr(self::challenge($i . $action . $uid), -12, 10) == $crumb ||    
            substr(self::challenge(($i - 1) . $action . $uid), -12, 10) == $crumb)    
            return true;                                                                                        
        return false;    

The $uid in the code indicates that the user is identified only by 1, and $ttl indicates the validity time of the random string.
The sample application
Structure form
Insert a hidden random string crumb into the form

<form method="post" action="demo.php">    
 <input type="hidden" name="crumb" value="<?php echo Crumb::issueCrumb($uid)?>">    
 <input type="text" name="content">    
 <input type="submit">    

Process the form demo.php
Conduct an inspection of crumb

if(Crumb::verifyCrumb($uid, $_POST['crumb'])) {    
    // Process the form as normal     
} else {    
    //crumb Validation failed, error prompt process     

This article is from baozi blog

Related articles: