PHP 之 JWT

时间:2020-03-26
本文章向大家介绍PHP 之 JWT,主要包括PHP 之 JWT使用实例、应用技巧、基本知识点总结和需要注意事项,具有一定的参考价值,需要的朋友可以参考一下。
1.JWT
网址:https://packagist.org/packages/tymon/jwt-auth

composer require tymon/jwt-auth dev-master
调用:

$data = TokenService::getToken($adminFind);
<?php


namespace App\Common\Services;


use App\Common\Model\Admin;
use App\Exceptions\ParamException;
use App\Exceptions\TokenException;
use App\Exceptions\TokenRefreshException;
use Firebase\JWT\JWT;
use Illuminate\Support\Facades\Cache;
use Illuminate\Support\Facades\Config;
use Illuminate\Support\Facades\Request;

class TokenService
{
    /**
     * @param $cacheValue
     * @return string|null
     * @throws ParamException
     * @author:  deng    (2020/2/12 11:57)
     */
    public function createToken($cacheValue)
    {
        //  key
        $key = $this->createStr();

        //  value   数组格式转换json字符串
        $value = json_encode($cacheValue);

        //  time
        $expire_in = Config::get('web.token_expire_in');

        //  添加到缓存中
        $result = Cache::put($key, $value, $expire_in);

        if (!$result) {
            throw new ParamException('服务器缓存异常');
        }

        return $key;
    }

    /**
     * @return string|null
     */
    public function createStr()
    {
        $length = 30;
        $str = null;
        $strPol = "ABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789abcdefghijklmnopqrstuvwxyz";
        $max = strlen($strPol) - 1;

        for ($i = 0; $i < $length; $i++) {
            $str .= $strPol[rand(0, $max)];
        }

        return $str;
    }

    /**
     * JWT 创建jwt入口
     *
     * @param $user
     * @return array
     * @author:  deng    (2020-03-11 15:09)
     */
    public static function getToken($user)
    {
        //  访问的令牌
        $accessToken = self::createAccessToken($user);
        //  刷新的令牌
        $refreshToken = self::createRefreshToken($user);
        return [
            'access_token' => $accessToken,
            'refresh_token' => $refreshToken
        ];
    }

    /**
     * 访问的令牌
     *
     * @param $user
     * @return mixed
     * @author:  deng    (2020-03-11 15:10)
     */
    private static function createAccessToken($user)
    {
        $key = config('secure.access_token_salt');
        $payload = [
            'iss' => 'lin-cms-tp5', //签发者
            'iat' => time(), //什么时候签发的
            'exp' => time() + 7200, //过期时间
            'user' => $user,
        ];

        return JWT::encode($payload, $key);
    }

    /**
     * @param $user
     * @return mixed
     * @author:  deng    (2020-03-11 15:10)
     */
    private static function createRefreshToken($user)
    {
        $key = config('secure.refresh_token_salt');
        $payload = [
            'iss' => 'lin-cms-tp5', //签发者
            'iat' => time(), //什么时候签发的
            'exp' => time() + 604800, //过期时间,一个星期
            'user' => ['id' => $user->id],
        ];

        return JWT::encode($payload, $key);
    }

    /**
     * @return array
     * @throws ParamException
     * @throws TokenException
     */
    public static function refreshToken()
    {
        try {
            $user_id = self::getCurrentTokenVar('id','refresh_token_salt');
            $user = Admin::query()->find($user_id);
            $accessToken = self::createAccessToken($user);
        } catch (TokenException $ex) {



            throw new TokenException($ex->msg);
        }

        return [
            'access_token' => $accessToken,
        ];
    }

    /**
     * @return mixed
     * @throws ParamException
     * @throws TokenException
     * @author:  deng    (2020-03-11 20:10)
     */
    public static function getTokenJwtId()
    {
        return self::getCurrentTokenVar('id');
    }

    /**
     * @param $key
     * @param string $tokenType
     * @return mixed
     * @throws ParamException
     * @throws TokenException
     * @author:  deng    (2020-03-11 20:08)
     */
    private static function getCurrentTokenVar($key, $tokenType = 'access_token_salt')
    {
        $authorization = Request::header('authorization');

        if (!$authorization) {
            throw new TokenException('请求未携带Authorization信息');
//            throw new TokenException(['msg' => '请求未携带Authorization信息']);
        }

        list($type, $token) = explode(' ', $authorization);

        if ($type !== 'Bearer') throw new TokenException('接口认证方式需为Bearer');

        if (!$token || $token === 'undefined') {
            throw new TokenException('尝试获取的Authorization信息不存在');
        }

        $secretKey = config("secure.{$tokenType}");

        try {
            $jwt = (array)JWT::decode($token, $secretKey, ['HS256']);
        } catch (\Firebase\JWT\SignatureInvalidException $e) {  //签名不正确
            throw new TokenException('令牌签名不正确,请确认令牌有效性或令牌类型');
        } catch (\Firebase\JWT\BeforeValidException $e) {  // 签名在某个时间点之后才能用
            throw new TokenException('令牌尚未生效');
        } catch (\Firebase\JWT\ExpiredException $e) {  // token过期
            throw new TokenRefreshException('令牌已过期,刷新浏览器重试');
//            throw new TokenException('令牌已过期,刷新浏览器重试', 10050);
        } catch (\Exception $e) {  //其他错误
            throw new ParamException($e->getMessage());
        }
        if (array_key_exists($key, $jwt['user'])) {
            return $jwt['user']->$key;
        } else {
            throw new TokenException('尝试获取的Token变量不存在');
        }

    }
}

原文地址:https://www.cnblogs.com/vip-deng-vip/p/12577001.html