• 微服务(二) php laravel 用户客户端


    本节主要讲解通过laravel 作为客户端调用go kratos 服务端,实现用户注册登录

    环境

    docker desk
    laradock
    laravel

    环境准备

    1. 通过laradock php-fpm 安装 grpc protobuf
    2. workspace 安装protoc安装 protoc 与 grpc_php_plugin 可执行文件(这个plugin创建整很久)
    3. 为方便把grpc_php_plugin放到GRPC文件目录
    4. 在worksapce使用protoc 与 grpc_php_plugin 生成客户端代码
    protoc --proto_path=./ --php_out=./php-src/ --grpc_out=./php-src/ --plugin=protoc-gen-grpc=./grpc_php_plugin  ./api/user/v1/user.proto
    
    • 1

    生成客户端代码
    在这里插入图片描述

    实现

    1. 添加客户端调用服务层代码
      在这里插入图片描述
    2. 添加grpc 调用组件及GRPC服务的自动加载
    composer require grpc/grpc
    composer require google/protobuf
    
    • 1
    • 2

    grpc 服务文件自动加载

    "autoload": {
            "psr-4": {
                "App\\": "app/",
                "Database\\Factories\\": "database/factories/",
                "Database\\Seeders\\": "database/seeders/",
                "GPBMetadata\\":"GRPC/php-src/GPBMetadata/",
                "":"GRPC/php-src/"
            }
        },
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    1. 增加jwt 中间件
    composer require firebase/php-jwt
    
    • 1

    添加中间件app/Http/Middleware/ApiJwt.php

    
    
    namespace App\Http\Middleware;
    
    use App\Service\Jwt;
    use Closure;
    use Illuminate\Http\Request;
    
    class ApiJwt
    {
        /**
         * Handle an incoming request.
         *
         * @param \Illuminate\Http\Request $request
         * @param \Closure(\Illuminate\Http\Request): (\Illuminate\Http\Response|\Illuminate\Http\RedirectResponse)  $next
         * @return \Illuminate\Http\Response|\Illuminate\Http\RedirectResponse
         */
        public function handle(Request $request, Closure $next)
        {
            //将token放入header中传输
            $token = $request->header('Authorization');
            if (!$token) {
                return response()->json(['code' => 500, 'msg' => 'token不存在', 'data' => []]);
            }
            $result = Jwt::decodeToken($token);
            if ($result) {
                //将加密id解密传入下一步
                $request->attributes->add(['user_id' => $result->user_id, 'nickname' => $result->nickname]);
            } else {
                return response()->json(['code' => 500, 'msg' => 'token过期', 'data' => []]);
            }
            return $next($request);
        }
    }
    
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35

    添加jwt 服务app/Service/Jwt.php

    
    namespace App\Service;
    
    use Firebase\JWT\JWT as JwtService;
    use Firebase\JWT\Key;
    
    class Jwt
    {
        protected static $key = 'laravel-tiway';
    
        //加密
        public static function createToken($userId, $nickname)
        {
            $payload = array(
                "iss" => "http://example.org",
                "aud" => "http://example.com",
                'exp' => time() + (24 * 3600),
                'user_id' => $userId,
                'nickname' => $nickname,
            );
            $jwt = JwtService::encode($payload, self::$key, 'HS256');
            return $jwt;
        }
    
        //解密
        public static function decodeToken($jwt)
        {
            $decoded = JwtService::decode($jwt, new Key(self::$key, 'HS256'));
            if ($decoded) {
                return $decoded;
            } else {
                return false;
            }
    
        }
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    1. 实现登录注册 app/Http/Controllers/UserController.php
    
    
    namespace App\Http\Controllers;
    
    use App\Service\GrpcUser;
    use App\Service\Jwt;
    use Illuminate\Http\Request;
    
    class UserController extends Controller
    {
        /**
         * @param Request $request
         * @return \Illuminate\Http\JsonResponse
         * @throws \Exception
         */
        public function register(Request $request)
        {
            $input = $request->only('nickname', 'mobile', 'password');
            //用户手机号码是否已注册
            $user = GrpcUser::getUserByMobile($input['mobile']);
            if (isset($user['id'])) {
                throw new \Exception('手机号码已被注册');
            }
            //创建用户
            $user = GrpcUser::CreateUser($input['nickname'], $input['mobile'], $input['password']);
            if (!isset($user['id'])) {
                throw new \Exception('创建失败');
            }
    
            return response()->json([
                'success' => true,
                'data' => $user
            ], 200);
        }
    
        /**
         * @param Request $request
         * @return \Illuminate\Http\JsonResponse
         * @throws \Exception
         */
        public function login(Request $request)
        {
            $input = $request->only('mobile', 'password');
            //是否已经存在相同手机号码
            $isLogin = GrpcUser::checkoutUserPassword($input['mobile'], $input['password']);
            if (!$isLogin) {
                throw new \Exception('账号或密码错误');
            }
            //获取用户信息
            $user = GrpcUser::getUserByMobile($input['mobile']);
            //jwt
            if (isset($user['id'])) {
                $token = Jwt::createToken($user['id'], $user['nickname']);
            }
    
            return response()->json([
                'success' => true,
                'token' => $token,
            ]);
        }
    
        /**
         * @param Request $request
         * @return \Illuminate\Http\JsonResponse
         */
        public function getUser(Request $request)
        {
            $userId = $request->attributes->get('user_id');
            $user = GrpcUser::getUserById($userId);
            return response()->json(['user' => $user]);
        }
    
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    • 37
    • 38
    • 39
    • 40
    • 41
    • 42
    • 43
    • 44
    • 45
    • 46
    • 47
    • 48
    • 49
    • 50
    • 51
    • 52
    • 53
    • 54
    • 55
    • 56
    • 57
    • 58
    • 59
    • 60
    • 61
    • 62
    • 63
    • 64
    • 65
    • 66
    • 67
    • 68
    • 69
    • 70
    • 71
    • 72
    • 73

    代码参考:laravel-tiway

    总结

    1. 后期有时间把用户信息全部添加一个redis 缓存
    2. 简化controller,添加仓库层实现数据
    3. 如果你也是用docker desk,为求方便,联系我,我将提供workspace 和php-fpm 的镜像压缩包
  • 相关阅读:
    Talk | UCSD博士生刘明华:在开放的世界中理解和生成3D物体
    【题目讲解】等腰三角形
    高级篇之ENC编码器多机位帧同步配置详解
    程序员的浪漫
    vue3 生命周期函数,都改了啥?
    减少Cache失效开销例题1(多级Cache)
    JVM运行参数之-X和-XX参数
    JS教程之使用 ElectronJS 桌面应用程序打印贴纸/标签
    【分布式系统】分布式选举之Bully算法
    蓝牙 - BLE SPP实现举例 (Bluecode Protocol Stack)
  • 原文地址:https://blog.csdn.net/qq_39941141/article/details/127448438