doushuangdui5419 2017-05-04 10:07
浏览 75

在auth中间件中使用缓存

I'd like to write own auth route middleware to use user cache. If I will simple check with cache in DB user then I see

Call to a member function setCookie() on null

I should use UserProvider probably. But then I don't use cache.

Does it any way to return same result like original auth but set cache inside?

My current code is:

<?php
namespace Sakuicms\Auth\Middleware;

use Closure;
use Illuminate\Contracts\Auth\Factory as Auth;
use Illuminate\Auth\AuthenticationException;


class Authenticate
{
    protected $auth;

    public function __construct(Auth $auth)
    {
      $this->auth = $auth;
    }

    protected function getName()
    {
      return 'login_'.config('auth.defaults.guard').'_'.sha1('Illuminate\Auth\SessionGuard');
    }

    public function handle($request, Closure $next, ...$guards)
    {
      $id = session($this->getName());
      if($id>0){
        $model = config('auth.providers.users.model');
        return \Cache::rememberForever('db.users.'.$id, function() use($model,$id){
          return $model::select(['id'])->where('id',$id)->first();
        });
      }
      throw new AuthenticationException('Unauthenticated.', $guards);
      return $next($request);
    }

}

EDIT I solve this problem. Of course it was my wrong. I always return not $next($request) but clear user object

Below is code which work

<?php
namespace Sakuicms\Auth\Middleware;

use Closure;
use Illuminate\Contracts\Auth\Factory as Auth;
use Illuminate\Auth\AuthenticationException;
use Sakuicms\Auth\SessionGuard;

class Authenticate
{
    protected $auth;

    public function __construct(Auth $auth)
    {
      $this->auth = $auth;
    }

    protected function getName()
    {
      return 'login_'.config('auth.defaults.guard').'_'.sha1('Illuminate\Auth\SessionGuard');
    }

    public function handle($request, Closure $next, ...$guards)
    {
      $this->authenticate($guards);
      return $next($request);
    }

    protected function authenticate(array $guards)
    {
      if(empty($guards)){
        $id = session($this->getName());
        if($id>0){
          $model = config('auth.providers.users.model');
          return \Cache::rememberForever('db.users.'.$id, function() use($model,$id){
            return $model::select(['id'])->where('id',$id)->first();
          });
        }
      }

      foreach ($guards as $guard) {
          if ($this->auth->guard($guard)->check()) {
              return $this->auth->shouldUse($guard);
          }
      }

      throw new AuthenticationException('Unauthenticated.', $guards);
    }

}

Probably exists better/more elegant solution but for now it's ok for me. I'll refactor it in next stage.

  • 写回答

0条回答 默认 最新

    报告相同问题?

    悬赏问题

    • ¥50 potsgresql15备份问题
    • ¥15 Mac系统vs code使用phpstudy如何配置debug来调试php
    • ¥15 目前主流的音乐软件,像网易云音乐,QQ音乐他们的前端和后台部分是用的什么技术实现的?求解!
    • ¥60 pb数据库修改与连接
    • ¥15 spss统计中二分类变量和有序变量的相关性分析可以用kendall相关分析吗?
    • ¥15 拟通过pc下指令到安卓系统,如果追求响应速度,尽可能无延迟,是不是用安卓模拟器会优于实体的安卓手机?如果是,可以快多少毫秒?
    • ¥20 神经网络Sequential name=sequential, built=False
    • ¥16 Qphython 用xlrd读取excel报错
    • ¥15 单片机学习顺序问题!!
    • ¥15 ikuai客户端多拨vpn,重启总是有个别重拨不上