2020-01-07 17:27:55 +08:00
|
|
|
<?php
|
2020-11-29 09:29:14 +08:00
|
|
|
declare(strict_types=1);
|
|
|
|
|
2020-01-07 17:27:55 +08:00
|
|
|
namespace catcher;
|
|
|
|
|
2020-09-09 10:40:44 +08:00
|
|
|
use catchAdmin\permissions\model\Users;
|
2020-01-07 17:27:55 +08:00
|
|
|
use catcher\exceptions\FailedException;
|
|
|
|
use catcher\exceptions\LoginFailedException;
|
|
|
|
use thans\jwt\facade\JWTAuth;
|
|
|
|
use think\facade\Session;
|
2020-09-09 10:40:44 +08:00
|
|
|
use think\helper\Str;
|
2020-01-07 17:27:55 +08:00
|
|
|
|
|
|
|
class CatchAuth
|
|
|
|
{
|
2021-01-27 14:01:17 +08:00
|
|
|
/**
|
|
|
|
* @var mixed
|
|
|
|
*/
|
2020-01-07 17:27:55 +08:00
|
|
|
protected $auth;
|
|
|
|
|
2021-01-27 14:01:17 +08:00
|
|
|
/**
|
|
|
|
* @var mixed
|
|
|
|
*/
|
2020-01-07 17:27:55 +08:00
|
|
|
protected $guard;
|
|
|
|
|
|
|
|
// 默认获取
|
|
|
|
protected $username = 'email';
|
2021-01-27 14:01:17 +08:00
|
|
|
|
2020-01-07 17:27:55 +08:00
|
|
|
// 校验字段
|
|
|
|
protected $password = 'password';
|
|
|
|
|
2020-05-23 11:10:28 +08:00
|
|
|
// 保存用户信息
|
2020-05-23 14:04:23 +08:00
|
|
|
protected $user = [];
|
2020-05-23 11:10:28 +08:00
|
|
|
|
2021-01-27 14:01:17 +08:00
|
|
|
/**
|
|
|
|
* @var bool
|
|
|
|
*/
|
|
|
|
protected $checkPassword = true;
|
|
|
|
|
2020-01-07 17:27:55 +08:00
|
|
|
public function __construct()
|
|
|
|
{
|
|
|
|
$this->auth = config('catch.auth');
|
2020-07-14 12:21:29 +08:00
|
|
|
|
|
|
|
$this->guard = $this->auth['default']['guard'];
|
2020-01-07 17:27:55 +08:00
|
|
|
}
|
|
|
|
|
2020-10-26 19:09:28 +08:00
|
|
|
/**
|
|
|
|
* set guard
|
|
|
|
*
|
|
|
|
* @time 2020年01月07日
|
|
|
|
* @param $guard
|
|
|
|
* @return $this
|
|
|
|
*/
|
2020-07-13 17:06:21 +08:00
|
|
|
public function guard($guard)
|
2020-01-07 17:27:55 +08:00
|
|
|
{
|
2020-10-26 19:09:28 +08:00
|
|
|
$this->guard = $guard;
|
2020-01-07 17:27:55 +08:00
|
|
|
|
2020-10-26 19:09:28 +08:00
|
|
|
return $this;
|
2020-01-07 17:27:55 +08:00
|
|
|
}
|
|
|
|
|
2020-10-26 19:09:28 +08:00
|
|
|
/**
|
|
|
|
*
|
|
|
|
* @time 2020年01月07日
|
|
|
|
* @param $condition
|
|
|
|
* @return mixed
|
|
|
|
*/
|
2020-01-07 17:27:55 +08:00
|
|
|
public function attempt($condition)
|
|
|
|
{
|
2020-09-09 10:40:44 +08:00
|
|
|
try {
|
2021-01-27 14:01:17 +08:00
|
|
|
|
2020-09-09 10:40:44 +08:00
|
|
|
$user = $this->authenticate($condition);
|
2021-01-27 14:01:17 +08:00
|
|
|
|
2020-09-09 10:40:44 +08:00
|
|
|
if (!$user) {
|
|
|
|
throw new LoginFailedException();
|
|
|
|
}
|
|
|
|
if ($user->status == Users::DISABLE) {
|
|
|
|
throw new LoginFailedException('该用户已被禁用|' . $user->username, Code::USER_FORBIDDEN);
|
|
|
|
}
|
2020-01-07 17:27:55 +08:00
|
|
|
|
2021-01-27 14:01:17 +08:00
|
|
|
if ($this->checkPassword && !password_verify($condition['password'], $user->password)) {
|
2020-09-09 10:40:44 +08:00
|
|
|
throw new LoginFailedException('登录失败|' . $user->username);
|
|
|
|
}
|
|
|
|
|
2020-10-26 19:09:28 +08:00
|
|
|
return $this->{$this->getDriver()}($user);
|
|
|
|
|
2020-09-09 10:40:44 +08:00
|
|
|
} catch (\Exception $exception) {
|
2020-10-26 19:09:28 +08:00
|
|
|
//
|
2020-01-07 17:27:55 +08:00
|
|
|
}
|
2020-09-09 10:40:44 +08:00
|
|
|
}
|
2020-01-07 17:27:55 +08:00
|
|
|
|
2020-09-09 10:40:44 +08:00
|
|
|
|
|
|
|
/**
|
|
|
|
* user
|
|
|
|
*
|
|
|
|
* @time 2020年09月09日
|
|
|
|
* @return mixed
|
|
|
|
*/
|
2020-01-07 17:27:55 +08:00
|
|
|
public function user()
|
|
|
|
{
|
2020-05-23 14:04:23 +08:00
|
|
|
$user = $this->user[$this->guard] ?? null;
|
|
|
|
|
|
|
|
if (!$user) {
|
2020-05-23 11:10:28 +08:00
|
|
|
switch ($this->getDriver()) {
|
|
|
|
case 'jwt':
|
|
|
|
$model = app($this->getProvider()['model']);
|
2020-05-23 14:04:23 +08:00
|
|
|
$user = $model->where($model->getPk(), JWTAuth::auth()[$this->jwtKey()])->find();
|
2020-05-23 11:10:28 +08:00
|
|
|
break;
|
|
|
|
case 'session':
|
2020-05-23 14:04:23 +08:00
|
|
|
$user = Session::get($this->sessionUserKey(), null);
|
2020-05-23 11:10:28 +08:00
|
|
|
break;
|
|
|
|
default:
|
|
|
|
throw new FailedException('user not found');
|
|
|
|
}
|
|
|
|
|
2020-05-23 14:04:23 +08:00
|
|
|
$this->user[$this->guard] = $user;
|
|
|
|
|
|
|
|
return $user;
|
2020-01-07 17:27:55 +08:00
|
|
|
}
|
2020-05-23 11:10:28 +08:00
|
|
|
|
2020-05-23 14:04:23 +08:00
|
|
|
return $user;
|
2020-01-07 17:27:55 +08:00
|
|
|
}
|
|
|
|
|
2020-10-26 19:09:28 +08:00
|
|
|
/**
|
|
|
|
*
|
|
|
|
* @time 2020年01月07日
|
|
|
|
* @return mixed
|
|
|
|
*/
|
2020-01-07 17:27:55 +08:00
|
|
|
public function logout()
|
|
|
|
{
|
2020-10-26 19:09:28 +08:00
|
|
|
switch ($this->getDriver()) {
|
|
|
|
case 'jwt':
|
|
|
|
return true;
|
|
|
|
case 'session':
|
|
|
|
Session::delete($this->sessionUserKey());
|
|
|
|
return true;
|
|
|
|
default:
|
|
|
|
throw new FailedException('user not found');
|
|
|
|
}
|
2020-01-07 17:27:55 +08:00
|
|
|
}
|
|
|
|
|
2020-10-26 19:09:28 +08:00
|
|
|
/**
|
|
|
|
*
|
|
|
|
* @time 2020年01月07日
|
|
|
|
* @param $user
|
|
|
|
* @return string
|
|
|
|
*/
|
2020-01-07 17:27:55 +08:00
|
|
|
protected function jwt($user)
|
|
|
|
{
|
2020-01-07 18:04:05 +08:00
|
|
|
$token = JWTAuth::builder([$this->jwtKey() => $user->id]);
|
2020-01-07 17:27:55 +08:00
|
|
|
|
2020-01-07 18:04:05 +08:00
|
|
|
JWTAuth::setToken($token);
|
2020-01-07 17:27:55 +08:00
|
|
|
|
2020-01-07 18:04:05 +08:00
|
|
|
return $token;
|
|
|
|
}
|
|
|
|
|
2020-10-26 19:09:28 +08:00
|
|
|
/**
|
|
|
|
*
|
|
|
|
* @time 2020年01月07日
|
|
|
|
* @param $user
|
|
|
|
* @return void
|
|
|
|
*/
|
2020-01-07 17:27:55 +08:00
|
|
|
protected function session($user)
|
|
|
|
{
|
|
|
|
Session::set($this->sessionUserKey(), $user);
|
|
|
|
}
|
|
|
|
|
2020-10-26 19:09:28 +08:00
|
|
|
/**
|
|
|
|
*
|
|
|
|
* @time 2020年01月07日
|
|
|
|
* @return string
|
|
|
|
*/
|
2020-01-07 17:27:55 +08:00
|
|
|
protected function sessionUserKey()
|
|
|
|
{
|
2020-10-26 19:09:28 +08:00
|
|
|
return $this->guard . '_user';
|
2020-01-07 17:27:55 +08:00
|
|
|
}
|
|
|
|
|
2020-10-26 19:09:28 +08:00
|
|
|
/**
|
|
|
|
*
|
|
|
|
* @time 2020年01月07日
|
|
|
|
* @return string
|
|
|
|
*/
|
2020-01-07 18:04:05 +08:00
|
|
|
protected function jwtKey()
|
|
|
|
{
|
2020-10-26 19:09:28 +08:00
|
|
|
return $this->guard . '_id';
|
2020-01-07 18:04:05 +08:00
|
|
|
}
|
|
|
|
|
2020-10-26 19:09:28 +08:00
|
|
|
/**
|
|
|
|
*
|
|
|
|
* @time 2020年01月07日
|
|
|
|
* @return mixed
|
|
|
|
*/
|
2020-01-07 17:27:55 +08:00
|
|
|
protected function getDriver()
|
|
|
|
{
|
2020-10-26 19:09:28 +08:00
|
|
|
return $this->auth['guards'][$this->guard]['driver'];
|
2020-01-07 17:27:55 +08:00
|
|
|
}
|
|
|
|
|
2020-10-26 19:09:28 +08:00
|
|
|
/**
|
|
|
|
*
|
|
|
|
* @time 2020年01月07日
|
|
|
|
* @return mixed
|
|
|
|
*/
|
2020-01-07 17:27:55 +08:00
|
|
|
protected function getProvider()
|
|
|
|
{
|
2020-07-13 09:03:59 +08:00
|
|
|
if (!isset($this->auth['guards'][$this->guard])) {
|
|
|
|
throw new FailedException('Auth Guard Not Found');
|
|
|
|
}
|
|
|
|
|
2020-01-07 17:27:55 +08:00
|
|
|
return $this->auth['providers'][$this->auth['guards'][$this->guard]['provider']];
|
|
|
|
}
|
|
|
|
|
2020-10-26 19:09:28 +08:00
|
|
|
/**
|
|
|
|
*
|
|
|
|
* @time 2020年01月07日
|
|
|
|
* @param $condition
|
|
|
|
* @return mixed
|
|
|
|
*/
|
2020-01-07 17:27:55 +08:00
|
|
|
protected function authenticate($condition)
|
|
|
|
{
|
|
|
|
$provider = $this->getProvider();
|
|
|
|
|
|
|
|
return $this->{$provider['driver']}($condition);
|
|
|
|
}
|
|
|
|
|
2020-10-26 19:09:28 +08:00
|
|
|
/**
|
|
|
|
*
|
|
|
|
* @time 2020年01月07日
|
|
|
|
* @param $condition
|
|
|
|
* @return void
|
|
|
|
*/
|
2020-01-07 17:27:55 +08:00
|
|
|
protected function database($condition): void
|
|
|
|
{}
|
|
|
|
|
2020-10-26 19:09:28 +08:00
|
|
|
/**
|
|
|
|
*
|
|
|
|
* @time 2020年01月07日
|
|
|
|
* @param $condition
|
|
|
|
* @return mixed
|
|
|
|
*/
|
2020-01-07 17:27:55 +08:00
|
|
|
protected function orm($condition)
|
|
|
|
{
|
|
|
|
return app($this->getProvider()['model'])->where($this->filter($condition))->find();
|
|
|
|
}
|
|
|
|
|
2020-10-26 19:09:28 +08:00
|
|
|
/**
|
|
|
|
*
|
|
|
|
* @time 2020年01月07日
|
|
|
|
* @param $condition
|
|
|
|
* @return array
|
|
|
|
*/
|
2020-01-07 17:27:55 +08:00
|
|
|
protected function filter($condition): array
|
|
|
|
{
|
|
|
|
$where = [];
|
|
|
|
|
|
|
|
foreach ($condition as $field => $value) {
|
2020-10-26 19:09:28 +08:00
|
|
|
if ($field != $this->password) {
|
|
|
|
$where[$field] = $value;
|
|
|
|
}
|
2020-01-07 17:27:55 +08:00
|
|
|
}
|
|
|
|
|
|
|
|
return $where;
|
|
|
|
}
|
|
|
|
|
2020-10-26 19:09:28 +08:00
|
|
|
/**
|
|
|
|
*
|
|
|
|
* @time 2020年01月07日
|
|
|
|
* @param $field
|
|
|
|
* @return $this
|
|
|
|
*/
|
2020-01-07 17:27:55 +08:00
|
|
|
public function username($field): self
|
|
|
|
{
|
|
|
|
$this->username = $field;
|
|
|
|
|
|
|
|
return $this;
|
|
|
|
}
|
|
|
|
|
2020-10-26 19:09:28 +08:00
|
|
|
/**
|
|
|
|
*
|
|
|
|
* @time 2020年01月07日
|
|
|
|
* @param $field
|
|
|
|
* @return $this
|
|
|
|
*/
|
2020-01-07 17:27:55 +08:00
|
|
|
public function password($field): self
|
|
|
|
{
|
|
|
|
$this->password = $field;
|
|
|
|
|
|
|
|
return $this;
|
|
|
|
}
|
2021-01-27 14:01:17 +08:00
|
|
|
|
|
|
|
/**
|
|
|
|
* 忽略密码认证
|
|
|
|
*
|
|
|
|
* @time 2021年01月27日
|
|
|
|
* @return $this
|
|
|
|
*/
|
|
|
|
public function ignorePasswordVerify(): CatchAuth
|
|
|
|
{
|
|
|
|
$this->checkPassword = false;
|
|
|
|
|
|
|
|
return $this;
|
|
|
|
}
|
2020-01-07 17:27:55 +08:00
|
|
|
}
|