创建一个移动端测试应用

composer create-project --prefer-dist laravel/laravel testapp

要让移动端应用和后端应用之间进行授权认证,需要在后端应用 blog 中注册对应的移动端应用 testapp,在 blog 项目根目录下运行以下命令来注册 testapp

php artisan passport:client --password
testapp
# 显示结果
CLIENT_ID=7
CLIENT_SECRET=2JPrCvRyoJ14f0OqCe6nnQZNDfPLNNPY7TcfDnco

testapp 应用中,将借助 Laravel 自带的认证脚手架快速实现认证路由和视图,以完成登录表单和请求提交:

php artisan make:auth

Auth/LoginController 控制器中重写 login 方法,将默认到数据库查询用户登录凭证的逻辑改为将请求发送到后端应用获取授权令牌:

// 在控制器顶部引入如下命名空间
use GuzzleHttp\Client;
use Illuminate\Http\Request;

// 重写 AuthenticatesUsers 中的 login 方法
public function login(Request $request)
{
    $request->validate([
        'email' => 'required|string',
        'password' => 'required|string',
    ]);

    $http = new Client();
    // 发送相关字段到后端应用获取授权令牌
    $response = $http->post('http://blog.test/oauth/token', [
        'form_params' => [
            'grant_type' => 'password',
            'client_id' => 7,
            'client_secret' => "2JPrCvRyoJ14f0OqCe6nnQZNDfPLNNPY7TcfDnco",
            'username' => $request->input('email'),
            'password' => $request->input('password'),
            'scope' => '*'
        ],
    ]);

    return response($response->getBody());
}

访问移动端应用登录页面 http://app.test/login,输入在后端应用 blog 中注册过的用户信息,点击登录,会将用户登录凭证和应用配置传递到后端应用的 oauth/token 路由,通过后端应用中 Passport 底层的密码授权类进行校验,校验成功后就会返回令牌信息给移动端应用。

返回结果中包含四个字段:

  • access_token 是授权令牌,可以将这个值设置到 Bearer Authentication 请求头去请求需要认证的后端 API 接口
  • token_type 表示认证类型是 Bearer
  • refresh_token 用于在令牌过期后刷新令牌
  • expires_in 表示令牌的有效期(单位是秒,即有效期一年)

在 Postman 中请求后端 API 接口 http://blog.test/api/user ,选择请求 Authorization 的类型为 Bearer Token,然后将 access_token 值拷贝到 Token 字段中,发起请求就可以获取到认证接口返回数据了。

后端应用设置令牌的有效期

可以在 AuthServiceProviderboot 方法中通过 Passport 门面上的 tokensExpireInrefreshTokensExpireIn 方法来设置令牌有效期:

Passport::tokensExpireIn(now()->addDays(7));
# 或
Passport::refreshTokensExpireIn(now()->addDays(7));

前端应用刷新令牌

当授权访问令牌过期后,可以请求 oauth/token 路由并指定操作类型为 refresh_token 来刷新令牌:

$http = new GuzzleHttp\Client;

$response = $http->post('http://blog.test/oauth/token', [
    'form_params' => [
        'grant_type' => 'refresh_token',
        'refresh_token' => 'your-refresh-token',
        'client_id' => 'your-client-id',
        'client_secret' => 'your-client-secret',
        'scope' => '*',
    ],
]);

return response($response->getBody());

刷新令牌后,会生成新的令牌并返回,同时将老的令牌撤销。


小伍
139 声望4 粉丝

引用和评论

0 条评论