laravel5.5安装jwt-auth 生成token令牌的示例


Posted in PHP onOctober 24, 2019

1:首先通过composer进行安装

composer require tymon/jwt-auth

laravel5.5安装jwt-auth 生成token令牌的示例

2:添加服务提供者

编辑 config/app.php,在 "providers" 添加:

'Tymon\JWTAuth\Providers\JWTAuthServiceProvider',

laravel5.5安装jwt-auth 生成token令牌的示例

3:添加 Facades

编辑 config/app.php,在 "alias" 添加:

'JWTAuth' => 'Tymon\JWTAuth\Facades\JWTAuth',

'JWTFactory' => 'Tymon\JWTAuth\Facades\JWTFactory',

laravel5.5安装jwt-auth 生成token令牌的示例

4:发布配置文件:

php artisan vendor:publish --provider="Tymon\JWTAuth\Providers\JWTAuthServiceProvider"

laravel5.5安装jwt-auth 生成token令牌的示例

5:生成 secret key

: php artisan jwt:generate

安装完成后,执行 php artisan jwt:generate,会报错:

(1).Method Tymon\JWTAuth\Commands\JWTGenerateCommand::handle() does not exist

解决方法,这个需要修改源码:

编辑 vendor/tymon/jwt-auth/src/Commands/JWTGenerateCommand.php,新增:

/**
 * Compatiblity with Laravel >= 5.5
*/
 public function handle()
 {
  $this->fire();
 }

(2)如果未添加服务提供者,直接执行该命令,可能也会报错!

There are no commands defined in the "jwt" namespace

解决方法:

就是上面的添加服务提供者

配置(Configuration)

secret(secret key) - 秘钥

用来签名 token 的秘钥。作者将秘钥与 Laravel 的 APP_KEY 分开,以便开发者可以独立地修改它们。

提供了一个 artisan 命令,为我们生成一个随机秘钥。(php artisan jwt:generate)

ttl(token time to live) - token 生存时间

token 的有效时间,以分钟为单位。建议尽可能设置短点,尤其是当我们也使用 token 刷新机制。

refresh_ttl(refresh time to live) - refresh 生存时间

可以刷新 token 的有效时间,以分钟为单位。例如,如果设置为 2周,那么只能在 2周 内,刷新对应的 token,否则将会抛出 TokenExpiredException 异常。如果超过了刷新的有效时间,必须生成一个全新的 token,这意味着用户需要重新登录。

注:ttl 和 refresh_ttl,用于保持用户的登录状态

algo(hashing algorithm) - hash 算法

用于签名 token 的算法,保留默认值即可

user(user model path) - 用户模型路径

应该指向我们项目的 User 类的命名空间路径

identifier(user identifier) - 用户标识

从 token 的主题声明中,根据什么标识来检索用户(一般是 id)

required_claims(required claims)

这些声明必须存在于 token 的 payload 中,否则将抛出 TokenInvalidException 异常(会检测 token 的 payload 是否存在这些声明)

blacklist_enabled(blacklist enabled)

如果设置为 false,将无法使 token 失效。虽然我们仍然可以刷新令牌,但是之前的令牌仍旧有效,因此这样做非常不安全。但对于非常简单的实现,可能不需要额外的开销(刷新 token 等),我们可以配置它。

providers

jwt-auth 包已经有一些具体实现,可用来实现各种需求。只要遵循相关接口,我们就可以覆盖这些具体实现。

providers.user

指定基于主题声明,来查找用户的实现。

providers.jwt

完成 token 的编码和解码的繁重工作

providers.auth

通过凭证或 id 来认证用户

providers.storage

用于驱动黑名单,并存储 token 直到过期。

创建 tokens(Creating Tokens)

jwt-auth 包为我们提供了创建 token 的多种方法。有简单的方法,如果你想更好的控制,也有更进一步的方法。

开箱即用(out of box),有许多必须的声明,虽然这些都可以配置:

sub(Subject) - 包含 token 的标识符(默认是用户 ID)

iat(Issued At) - token 发布时间(unix 时间戳)

exp(Expiry) - token 过期日期(unix 时间戳)

nbf(Not Before) - 可以使用 token 的最早时间点(unix 时间戳)

iss(Issuer) - token 发布者(默认为请求的 url)

jti(JWT Id) - token 的唯一标识符(sub 和 iat 声明的 md5 值)

aud(Audience) - token 的目标受众(默认不需要)

也允许自定义声明。稍后会介绍。

创建一个基于用户凭证的 token

创建 token 的最常用方法是,通过用户的登录凭证,来认证用户。如果认证成功,则返回一个与该用户相关的 token。例如,假设我们有一个 Laravel AuthenticateController

use JWTAuth;
use Tymon\JWTAuth\Exceptions\JWTException;
 
class AuthenticateController extends Controller
{
 public function authenticate(Request $request)
 {
  // grab credentials from the request
  $credentials = $request->only('email', 'password');
 
  try {
   // attempt to verify the credentials and create a token for the user
   if (! $token = JWTAuth::attempt($credentials)) {
    return response()->json(['error' => 'invalid_credentials'], 401);
   }
  } catch (JWTException $e) {
   // something went wrong whilst attempting to encode the token
   return response()->json(['error' => 'could_not_create_token'], 500);
  }
 
  // all good so return the token
  return response()->json(compact('token'));
 }
}

创建一个基于用户对象的 token

我们可以跳过用户认证,只传递一个用户对象

$user = User::first();
$token = JWTAuth::fromUser($user);

上面的 2 个方法也有第二个参数,可以传递一个 '自定义声明' 的数组

在解码 token 时,这些自定义声明,将和其他声明一起提供。

注意:添加大量的自定义声明,将增加 token 的大小

创建一个基于任意你喜欢的内容的 token

作者给我们提供了对底层类和方法的访问,来提供高级的、可自定义的功能。

示例使用了内建的 'Tymon\JWTAuth\PayloadFactory' 实例(或者使用 JWTFactory 门面):

$customClaims = ['foo' => 'bar', 'baz' => 'bob'];
$payload = JWTFactory::make($customClaims);
$token = JWTAuth::encode($payload);

也可以在 'Tymon\JWTAuth\PayloadFactory' 实例上链式调用声明(或者使用 JWTFactory 门面):

$payload = JWTFactory::sub(123)->aud('foo')->foo(['bar' => 'baz']);
$token = JWTAuth::encode($payload);

认证(Authentication)

一旦用户使用他们的凭证登录,下一步将使用 token 发起一个后续请求,来检索用户详情,以便我们可以将其显示为已登录。

使用内置方法,通过 http 发起认证请求,我们需要设置一个 Authorization 请求头,如下所示:

Authorization: Bearer {yourtokenhere}

Apache 用户需要注意:

Apache 好像会丢弃 Authorization 请求头,如果该请求头不是 base64 编码的 user/pass 组合。为了解决此问题,我们可以在 apache 配置文件中添加一下内容:

RewriteEngine On
  RewriteCond %{HTTP:Authorization} ^(.*)
  RewriteRule .* - [e=HTTP_AUTHORIZATION:%1]

或者,我们可以通过在查询字符串中包含 token 来实现:

http://api.mysite.com/me?token={yourtokenhere}

为了从请求中获取 token,我们可以:

// 会设置 token 到返回的对象中
JWTAuth::parseToken();
// 接着,我们可以继续链式调用方法
$user = JWTAuth::parseToken()->authenticate();

为了获取 token 的值,我们可以调用:

$token = JWTAuth::getToken();

如果设置了一个 token,则会返回 token,否则(为方便起见),它将使用上述方法,尝试从请求中解析 token,如果没有设置 token 或 没有 token 可以被解析,最终返回 false。

当然,如果在我们的程序中有其他入口点,我们也可以根据需要手动设置 token。例如:

JWTAuth::setToken('foo.bar.baz');

从 token 中检索认证过的用户

public function getAuthenticatedUser()
  {
   try {
    if(! $user = JWTAuth::parseToken()->authenticate()){
     return response()->json('user_not_found', 404);
    }
   } catch (Tymon\JWTAuth\Exceptions\TokenExpiredException $e) {
    return response()->json(['token_expired'], $e->getStatusCode());
   } catch (Tymon\JWTAuth\Exceptions\TokenInvalidException $e) {
    return response()->json(['token_invalid'], $e->getStatusCode());
   } catch (Tymon\JWTAuth\Exceptions\JWTException $e) {
    return response()->json(['token_absent'], $e->getStatusCode());
   }
   return response()->json(compact('user'));
  }

如果不喜欢内联捕获多个异常的方法,我们可以随意使用 Laravel 添加全局异常处理程序。

在 app/Exceptions/Handler.php 中,将下面代码添加到 render() 方法:

public function render($request, Exception $e)
  {
   if ($e instanceof Tymon\JWTAuth\Exceptions\TokenExpiredException) {
    return response()->json(['token_expired'], $e->getStatusCode());
   } else if ($e instanceof Tymon\JWTAuth\Exceptions\TokenInvalidException) {
    return response()->json(['token_invalid'], $e->getStatusCode());
   }
 
   return parent::render($request, $e);
  }

中间件和过滤器

如果我们使用的是 Laravel 5,可以使用内置的 2 个中间件:

GetUserFromToken

检查请求头和查询字符串(正如上面解释过的)是否存在 token,并尝试解码 token。如上所述,同样的事件被触发。

RefreshToken

此中间件将再次尝试从请求中解析 token,然后将刷新 token(从而使旧 token 失效),并将其作为下一次响应的一部分返回。这实际上产生了单个使用 token 流,如果 token 被泄露,这种方式会减少攻击,因为它仅对单个请求有效。

为了使用这 2 个中间件,我们需要将它们注册到 app/Http/Kernel.php 里的 $routeMIddleware 属性:

protected $routeMiddleware = [
    ...
    'jwt.auth' => 'Tymon\JWTAuth\Middleware\GetUserFromToken',
    'jwt.refresh' => 'Tymon\JWTAuth\Middleware\RefreshToken',
   ];

以上这篇laravel5.5安装jwt-auth 生成token令牌的示例就是小编分享给大家的全部内容了,希望能给大家一个参考,也希望大家多多支持三水点靠木。

PHP 相关文章推荐
我的论坛源代码(十)
Oct 09 PHP
php数组总结篇(一)
Sep 30 PHP
PHP foreach循环使用详解与实例代码
May 08 PHP
PHP Undefined index报错的修复方法
Jul 17 PHP
PHP URL参数获取方式的四种例子
Feb 28 PHP
ThinkPHP的L方法使用简介
Jun 18 PHP
关于扩展 Laravel 默认 Session 中间件导致的 Session 写入失效问题分析
Jan 08 PHP
PHP使用php-resque库配合Redis实现MQ消息队列的教程
Jun 29 PHP
Yii视图CGridView列表用法实例分析
Jul 12 PHP
PHP7基于curl实现的上传图片功能
May 11 PHP
基于PHP实现用户登录注册功能的详细教程
Aug 04 PHP
Nginx+php配置文件及原理解析
Dec 09 PHP
对laravel的csrf 防御机制详解,及form中csrf_token()的存在介绍
Oct 24 #PHP
Laravel (Lumen) 解决JWT-Auth刷新token的问题
Oct 24 #PHP
laravel5.1 ajax post 传值_token示例
Oct 24 #PHP
laravel 5.5 关闭token的3种实现方式
Oct 24 #PHP
Thinkphp 3.2框架使用Redis的方法详解
Oct 24 #PHP
laravel解决迁移文件一次删除创建字段报错的问题
Oct 24 #PHP
PHP Swoole异步读取、写入文件操作示例
Oct 24 #PHP
You might like
php MYSQL 数据备份类
2009/06/19 PHP
php中强制下载文件的代码(解决了IE下中文文件名乱码问题)
2011/05/09 PHP
PHP面向对象概念
2011/11/06 PHP
解析php中const与define的应用区别
2013/06/18 PHP
php设计模式之单例模式使用示例
2014/01/20 PHP
PHP 生成N个不重复的随机数
2015/01/21 PHP
ThinkPHP3.2.3数据库设置新特性
2015/03/05 PHP
php实现压缩合并js的方法【附demo源码下载】
2016/09/22 PHP
Yii2框架中使用PHPExcel导出Excel文件的示例
2017/08/09 PHP
PHP实现的超长文本分页显示功能示例
2018/06/04 PHP
Javascript 篱式条件判断
2008/08/22 Javascript
JavaScript 提升运行速度之循环篇 译文
2009/08/15 Javascript
学习ExtJS 访问容器对象
2009/10/07 Javascript
在Javascript中 声明时用"var"与不用"var"的区别
2013/04/15 Javascript
JavaScript利用append添加元素报错的解决方法
2014/07/01 Javascript
JS+CSS实现可拖拽的漂亮圆角特效弹出层完整实例
2015/02/13 Javascript
jQuery实现ajax无刷新分页页码控件
2017/02/28 Javascript
vue router demo详解
2017/10/13 Javascript
vue中使用element-ui进行表单验证的实例代码
2018/06/22 Javascript
JavaScript中发出HTTP请求最常用的方法
2018/07/12 Javascript
基于vue v-for 多层循环嵌套获取行数的方法
2018/09/26 Javascript
vue路由拦截器和请求拦截器知识点总结
2019/11/08 Javascript
使用vue实现HTML页面生成图片的方法
2020/03/12 Javascript
Vue项目利用axios请求接口下载excel
2020/11/17 Vue.js
python使用循环实现批量创建文件夹示例
2014/03/25 Python
Python-嵌套列表list的全面解析
2016/06/08 Python
python字符串与url编码的转换实例
2018/05/10 Python
Python numpy多维数组实现原理详解
2020/03/10 Python
python实现简单的井字棋游戏(gui界面)
2021/01/22 Python
canvas 绘图时位置偏离的问题解决
2020/09/16 HTML / CSS
New Balance加拿大官方网站:运动鞋和健身服装
2018/11/19 全球购物
正宗的日本零食和糖果订阅盒:Bokksu
2019/11/21 全球购物
Strathberry苏贝瑞中国官网:西班牙高级工匠手工打造
2020/10/19 全球购物
一份软件工程师的面试试题
2016/02/01 面试题
编辑找工作求职信范文
2013/12/16 职场文书
党员学习群众路线教育实践活动对照检查材料
2014/09/23 职场文书