php实现JWT验证的实例教程


Posted in PHP onNovember 26, 2020

JWT,全称 Json web token,是为了在网络应用环境间传递声明而执行的一种基于JSON的开放标准((RFC 7519).该token被设计为紧凑且安全的,特别适用于分布式站点的单点登录(SSO)场景。JWT的声明一般被用来在身份提供者和服务提供者间传递被认证的用户身份信息,以便于从资源服务器获取资源,也可以增加一些额外的其它业务逻辑所必须的声明信息,该token也可直接被用于认证,也可被加密。

php实现JWT,本例使用thinkphp框架,代码如下:

在vendor包中建立Jwt.php,建立类文件

class Jwt {
 
 //头部
 private static $header=array(
  'alg'=>'HS256', //生成signature的算法
  'typ'=>'JWT' //类型
 );
 
 //使用HMAC生成信息摘要时所使用的密钥
 private static $key='123456';
 
 
 /**
  * 获取jwt token
  * @param array $payload jwt载荷 格式如下非必须
  * [
  * 'iss'=>'jwt_admin', //该JWT的签发者
  * 'iat'=>time(), //签发时间
  * 'exp'=>time()+7200, //过期时间
  * 'nbf'=>time()+60, //该时间之前不接收处理该Token
  * 'sub'=>'www.admin.com', //面向的用户
  * 'jti'=>md5(uniqid('JWT').time()) //该Token唯一标识
  * ]
  * @return bool|string
  */
 public static function getToken($payload)
 {
  if(is_array($payload))
  {
   $base64header=self::base64UrlEncode(json_encode(self::$header,JSON_UNESCAPED_UNICODE));
   $base64payload=self::base64UrlEncode(json_encode($payload,JSON_UNESCAPED_UNICODE));
   $token=$base64header.'.'.$base64payload.'.'.self::signature($base64header.'.'.$base64payload,self::$key,self::$header['alg']);
   return $token;
  }else{
   return false;
  }
 }
 
 
 /**
  * 验证token是否有效,默认验证exp,nbf,iat时间
  * @param string $Token 需要验证的token
  * @return bool|string
  */
 public static function verifyToken($Token)
 {
  $tokens = explode('.', $Token);
  if (count($tokens) != 3)
   return false;
 
  list($base64header, $base64payload, $sign) = $tokens;
 
  //获取jwt算法
  $base64decodeheader = json_decode(self::base64UrlDecode($base64header), JSON_OBJECT_AS_ARRAY);
  if (empty($base64decodeheader['alg']))
   return false;
 
  //签名验证
  if (self::signature($base64header . '.' . $base64payload, self::$key, $base64decodeheader['alg']) !== $sign)
   return false;
 
  $payload = json_decode(self::base64UrlDecode($base64payload), JSON_OBJECT_AS_ARRAY);
 
  //签发时间大于当前服务器时间验证失败
  if (isset($payload['iat']) && $payload['iat'] > time())
   return false;
 
  //过期时间小宇当前服务器时间验证失败
  if (isset($payload['exp']) && $payload['exp'] < time())
   return false;
 
  //该nbf时间之前不接收处理该Token
  if (isset($payload['nbf']) && $payload['nbf'] > time())
   return false;
 
  return $payload;
 }
 
 
 
 
 /**
  * base64UrlEncode https://jwt.io/ 中base64UrlEncode编码实现
  * @param string $input 需要编码的字符串
  * @return string
  */
 private static function base64UrlEncode($input)
 {
  return str_replace('=', '', strtr(base64_encode($input), '+/', '-_'));
 }
 
 /**
  * base64UrlEncode https://jwt.io/ 中base64UrlEncode解码实现
  * @param string $input 需要解码的字符串
  * @return bool|string
  */
 private static function base64UrlDecode($input)
 {
  $remainder = strlen($input) % 4;
  if ($remainder) {
   $addlen = 4 - $remainder;
   $input .= str_repeat('=', $addlen);
  }
  return base64_decode(strtr($input, '-_', '+/'));
 }
 
 /**
  * HMACSHA256签名 https://jwt.io/ 中HMACSHA256签名实现
  * @param string $input 为base64UrlEncode(header).".".base64UrlEncode(payload)
  * @param string $key
  * @param string $alg 算法方式
  * @return mixed
  */
 private static function signature($input, $key, $alg = 'HS256')
 {
  $alg_config=array(
   'HS256'=>'sha256'
  );
  return self::base64UrlEncode(hash_hmac($alg_config[$alg], $input, $key,true));
 }
}

调用JWT验证的方法,代码如下:

1.构建token方法

public function makeToken(){
	 $uname=$this->uname;	$currtime=time();
	 if(empty($this->uname)){ echo json_encode(array('code'=>-1,'msg'=>'[主账号]参数为空'),JSON_UNESCAPED_UNICODE);	exit(); }	
	 ....
	 //jwt验证
	 vendor("Jwt.Jwt");
	 $jwt = new \Jwt();
//这里构造jwt参数,可以参照jwt规范,各字段可以自行定义内容	 $payload=array('iss'=>'xesport','sub'=>'xxx_player','name'=>$playerName,'iat'=>$currtime,'jti'=>md5(uniqid('JWT').$currtime));
	 $token=$jwt->getToken($payload); $this->token=$token;
	 $url='http://xxx?token='.$token;
	 $data=array('url'=>$url);
	 
	 echo json_encode(array('code'=>1,'data'=>$data,),JSON_UNESCAPED_UNICODE); exit();
 
	}

2.验证token的方法

//验证token
public function verifyToken(){
	 $token=$_REQUEST['token'];
	 if(empty($token)){ echo json_encode(array('code'=>-1,'msg'=>'[token]参数为空!'),JSON_UNESCAPED_UNICODE);	exit(); }
  vendor("Jwt.Jwt");
	 $jwt = new \Jwt();	 
	 $res_token=$jwt->verifyToken($token);
  //var_dump('res_token==',$res_token);
	 if(empty($res_token)){ echo json_encode(array('code'=>-2,'msg'=>'[token]验证失败!'),JSON_UNESCAPED_UNICODE);	exit(); }
	 $playerName=$res_token['name'];
	 //echo $playerName; die;
	 这里可以写从数据库查询验证user是否存在,返回 $userInfo 
	 if(empty($userInfo)){ echo json_encode(array('code'=>-3,'msg'=>'[token]验证用户无效!'),JSON_UNESCAPED_UNICODE);	exit(); }
	 $data=array('username'=>$playerName);
	 echo json_encode(array('code'=>1,'data'=>$data,'msg'=>'[token]验证成功'),JSON_UNESCAPED_UNICODE);	exit();
	}

这样,我们通过控制器方法调用该方法,传递参数token,就可以解析token中包含的认证凭据信息,从而做后续业务处理逻辑。

到此这篇关于php实现JWT验证的文章就介绍到这了,更多相关php实现JWT验证内容请搜索三水点靠木以前的文章或继续浏览下面的相关文章希望大家以后多多支持三水点靠木!

PHP 相关文章推荐
一个ftp类(ini.php)
Oct 09 PHP
php学习 字符串课件
Jun 15 PHP
php判断字符以及字符串的包含方法属性
Aug 30 PHP
PHP语言中global和$GLOBALS[]的分析 之二
Feb 02 PHP
PHP可逆加密/解密函数分享
Sep 25 PHP
PHP版 汉字转码的实现详解
Jun 09 PHP
php使用GeoIP库实例
Jun 27 PHP
详解WordPress中创建和添加过滤器的相关PHP函数
Dec 29 PHP
php中的常用魔术方法汇总
Feb 14 PHP
php blowfish加密解密算法
Jul 02 PHP
php实现二叉树中和为某一值的路径方法
Oct 14 PHP
php fread函数使用方法总结
May 28 PHP
PHP替换Word中变量并导出PDF图片的实现方法
Nov 26 #PHP
PHP扩展安装方法步骤解析
Nov 24 #PHP
Cookie跨域问题解决方案代码示例
Nov 24 #PHP
PHP执行linux命令6个函数代码实例
Nov 24 #PHP
PHP获取真实IP及IP模拟方法解析
Nov 24 #PHP
Thinkphp极验滑动验证码实现步骤解析
Nov 24 #PHP
ThinkPhP+Apache+PHPstorm整合框架流程图解
Nov 23 #PHP
You might like
第一个无线电台是由谁发明的
2021/03/01 无线电
php中通过smtp发邮件的类,测试通过
2007/01/22 PHP
Ext.data.PagingMemoryProxy分页一次性读取数据的实现代码
2010/04/07 PHP
PHP中的MYSQL常用函数(php下操作数据库必备)
2010/09/12 PHP
解析百度搜索结果link?url=参数分析 (全)
2012/10/09 PHP
如何利用php array_multisort函数 对数据库结果进行复杂排序
2013/06/08 PHP
Smarty中的注释和截断功能介绍
2015/04/09 PHP
php redis setnx分布式锁简单原理解析
2020/10/23 PHP
用javascript操作xml
2006/11/04 Javascript
浏览器脚本兼容 文本框中,回车键触发事件的兼容
2010/06/21 Javascript
javascript跑马灯悬停放大效果实现代码
2012/12/12 Javascript
JQuery切换显示的效果实例代码
2013/02/27 Javascript
使用js判断数组中是否包含某一元素(类似于php中的in_array())
2013/12/12 Javascript
2014 HTML5/CSS3热门动画特效TOP10
2014/12/07 Javascript
ztree获取当前选中节点子节点id集合的方法
2015/02/12 Javascript
基于jquery实现省市区三级联动效果
2015/12/25 Javascript
Javascript实现鼠标框选操作  不是点击选取
2016/04/14 Javascript
jQuery实现漂亮实用的商品图片tips提示框效果(无图片箭头+阴影)
2016/04/16 Javascript
jQuery中值得注意的trigger方法浅析
2016/12/12 Javascript
Vue结合原生js实现自定义组件自动生成示例
2017/01/21 Javascript
基于模板引擎Jade的应用(详解)
2017/12/12 Javascript
Vue实现移动端左右滑动效果的方法
2018/11/27 Javascript
JS基于开关思想实现的数组去重功能【案例】
2019/02/18 Javascript
二种python发送邮件实例讲解(python发邮件附件可以使用email模块实现)
2013/12/03 Python
Django的HttpRequest和HttpResponse对象详解
2018/01/26 Python
Django 中自定义 Admin 样式与功能的实现方法
2019/07/04 Python
python 实现倒计时功能(gui界面)
2020/11/11 Python
基于PyTorch中view的用法说明
2021/03/03 Python
AT&T Wireless:手机、无限数据计划和配件
2018/06/03 全球购物
美国台面电器和厨具品牌:KitchenAid
2019/04/12 全球购物
施华洛世奇匈牙利官网:SWAROVSKI匈牙利
2019/07/06 全球购物
计算机专业个人求职自荐信
2013/09/21 职场文书
会计应聘求职信范文
2013/12/17 职场文书
关于职业道德的心得体会
2016/01/18 职场文书
使用Cargo工具高效创建Rust项目
2022/08/14 Javascript
Java中的Kafka为什么性能这么快及4大核心详析
2022/09/23 Java/Android