TokenBuildBehavior.class.php 2.5 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061
  1. <?php
  2. // +----------------------------------------------------------------------
  3. // | TOPThink [ WE CAN DO IT JUST THINK ]
  4. // +----------------------------------------------------------------------
  5. // | Copyright (c) 2010 http://topthink.com All rights reserved.
  6. // +----------------------------------------------------------------------
  7. // | Licensed ( http://www.apache.org/licenses/LICENSE-2.0 )
  8. // +----------------------------------------------------------------------
  9. // | Author: liu21st <liu21st@gmail.com>
  10. // +----------------------------------------------------------------------
  11. defined('THINK_PATH') or exit();
  12. /**
  13. * 系统行为扩展:表单令牌生成
  14. * @category Think
  15. * @package Think
  16. * @subpackage Behavior
  17. * @author liu21st <liu21st@gmail.com>
  18. */
  19. class TokenBuildBehavior extends Behavior {
  20. // 行为参数定义
  21. protected $options = array(
  22. 'TOKEN_ON' => false, // 开启令牌验证
  23. 'TOKEN_NAME' => '__hash__', // 令牌验证的表单隐藏字段名称
  24. 'TOKEN_TYPE' => 'md5', // 令牌验证哈希规则
  25. 'TOKEN_RESET' => true, // 令牌错误后是否重置
  26. );
  27. public function run(&$content){
  28. if(C('TOKEN_ON')) {
  29. if(strpos($content,'{__TOKEN__}')) {
  30. // 指定表单令牌隐藏域位置
  31. $content = str_replace('{__TOKEN__}',$this->buildToken(),$content);
  32. }elseif(preg_match('/<\/form(\s*)>/is',$content,$match)) {
  33. // 智能生成表单令牌隐藏域
  34. $content = str_replace($match[0],$this->buildToken().$match[0],$content);
  35. }
  36. }else{
  37. $content = str_replace('{__TOKEN__}','',$content);
  38. }
  39. }
  40. // 创建表单令牌
  41. private function buildToken() {
  42. $tokenName = C('TOKEN_NAME');
  43. $tokenType = C('TOKEN_TYPE');
  44. if(!isset($_SESSION[$tokenName])) {
  45. $_SESSION[$tokenName] = array();
  46. }
  47. // 标识当前页面唯一性
  48. $tokenKey = md5($_SERVER['REQUEST_URI']);
  49. if(isset($_SESSION[$tokenName][$tokenKey])) {// 相同页面不重复生成session
  50. $tokenValue = $_SESSION[$tokenName][$tokenKey];
  51. }else{
  52. $tokenValue = $tokenType(microtime(TRUE));
  53. $_SESSION[$tokenName][$tokenKey] = $tokenValue;
  54. }
  55. $token = '<input type="hidden" name="'.$tokenName.'" value="'.$tokenKey.'_'.$tokenValue.'" />';
  56. return $token;
  57. }
  58. }