LoginService.php 7.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214
  1. <?php
  2. // +----------------------------------------------------------------------
  3. // | Niucloud-admin 企业快速开发的saas管理平台
  4. // +----------------------------------------------------------------------
  5. // | 官方网址:https://www.niucloud.com
  6. // +----------------------------------------------------------------------
  7. // | niucloud团队 版权所有 开源版本可自由商用
  8. // +----------------------------------------------------------------------
  9. // | Author: Niucloud Team
  10. // +----------------------------------------------------------------------
  11. namespace app\service\admin\auth;
  12. use app\dict\sys\AppTypeDict;
  13. use app\model\sys\SysUser;
  14. use app\model\sys\SysUserRole;
  15. use app\service\admin\captcha\CaptchaService;
  16. use app\service\admin\user\UserRoleService;
  17. use app\service\admin\user\UserService;
  18. use app\service\core\sys\CoreConfigService;
  19. use core\base\BaseAdminService;
  20. use core\exception\AuthException;
  21. use core\util\TokenAuth;
  22. use Throwable;
  23. /**
  24. * 登录服务层
  25. * Class BaseService
  26. * @package app\service
  27. */
  28. class LoginService extends BaseAdminService
  29. {
  30. public function __construct()
  31. {
  32. parent::__construct();
  33. $this->model = new SysUser();
  34. }
  35. /**
  36. * 用户登录
  37. * @param string $username
  38. * @param string $password
  39. * @param string $app_type
  40. * @return array|bool
  41. */
  42. public function login(string $username, string $password, string $app_type)
  43. {
  44. $this->site_id = $this->request->adminSiteId();
  45. if(!array_key_exists($app_type, AppTypeDict::getAppType())) throw new AuthException('APP_TYPE_NOT_EXIST');
  46. $config = (new ConfigService())->getConfig();
  47. switch($app_type){
  48. case AppTypeDict::SITE:
  49. $is_captcha = $config['is_site_captcha'];
  50. break;
  51. case AppTypeDict::ADMIN:
  52. $is_captcha = $config['is_captcha'];
  53. break;
  54. }
  55. if($is_captcha == 1){
  56. (new CaptchaService())->verification();
  57. }
  58. $user_service = new UserService();
  59. $userinfo = $user_service->getUserInfoByUsername($username);
  60. if ($userinfo->isEmpty()) return false;
  61. if (!check_password($password, $userinfo->password)) return false;
  62. $this->request->uid($userinfo->uid);
  63. if($app_type == AppTypeDict::ADMIN){
  64. $default_site_id = $this->request->defaultSiteId();
  65. $userrole = (new UserRoleService())->getUserRole($default_site_id, $userinfo->uid);
  66. if (!empty($userrole)) {
  67. if (!$userrole['status']) throw new AuthException('USER_LOCK');
  68. }
  69. // else {
  70. // $app_type = AppTypeDict::SITE;
  71. // }
  72. } else if($app_type == AppTypeDict::SITE){
  73. $site_ids = (new \app\service\admin\home\AuthSiteService())->getSiteIds();
  74. if(empty($site_ids)){
  75. throw new AuthException('SITE_NOT_EXIST');
  76. }else{
  77. $default_site_id = in_array($this->site_id, $site_ids) ? $this->site_id : $site_ids[0];
  78. }
  79. } else {
  80. throw new AuthException('APP_TYPE_NOT_EXIST');
  81. }
  82. //修改用户登录信息
  83. $userinfo->last_time = time();
  84. $userinfo->last_ip = app('request')->ip();
  85. $userinfo->login_count++;
  86. $userinfo->save();
  87. //创建token
  88. $token_info = $this->createToken($userinfo, $app_type);
  89. //查询权限以及菜单
  90. $data = [
  91. 'token' => $token_info['token'],
  92. 'expires_time' => $token_info['params']['exp'],
  93. 'userinfo' => [
  94. 'uid' => $userinfo->uid,
  95. 'username' => $userinfo->username,
  96. // 'is_super_admin' => AuthService::isSuperAdmin(),
  97. 'head_img' => $userinfo->head_img,
  98. ],
  99. 'site_id' => $default_site_id,
  100. 'site_info' => null,
  101. 'userrole' => $app_type == AppTypeDict::ADMIN ? $userrole : []
  102. ];
  103. if($app_type == AppTypeDict::ADMIN && empty($data['userrole']))
  104. throw new AuthException('NO_PERMISSION');
  105. if ($app_type == AppTypeDict::ADMIN || ($app_type == AppTypeDict::SITE && $data['site_id']) ) {
  106. $this->request->siteId($data['site_id']);
  107. $data['site_info'] = (new AuthSiteService())->getSiteInfo();
  108. }
  109. // 获取站点布局
  110. $layout_config = (new CoreConfigService())->getConfig($data['site_id'], 'SITE_LAYOUT');
  111. $data['layout'] = empty($layout_config) ? 'default' : $layout_config['value']['key'];
  112. return $data;
  113. }
  114. /**
  115. * 登陆退出(当前账户) (todo 这儿应该登出当前token, (登出一个账号还是全端口登出))
  116. * @return true
  117. */
  118. public function logout()
  119. {
  120. self::clearToken($this->uid, $this->app_type, $this->request->adminToken());
  121. return true;
  122. }
  123. /**
  124. * 创建token
  125. * @param SysUser $userinfo
  126. * @param string $app_type
  127. * @return array
  128. */
  129. public function createToken(SysUser $userinfo, string $app_type)
  130. {
  131. $expire_time = env('system.admin_token_expire_time') ?? 3600;
  132. return TokenAuth::createToken($userinfo->uid, AppTypeDict::ADMIN, ['uid' => $userinfo->uid, 'username' => $userinfo->username], $expire_time);
  133. }
  134. /**
  135. * 清理token
  136. * @param int $uid
  137. * @param string|null $type
  138. * @param string|null $token
  139. */
  140. public static function clearToken(int $uid, ?string $type = '', ?string $token = '')
  141. {
  142. if (empty($type)) {
  143. TokenAuth::clearToken($uid, AppTypeDict::ADMIN, $token);//清除平台管理端的token
  144. // TokenAuth::clearToken($uid, AppTypeDict::SITE, $token);//清除站点管理端的token
  145. } else {
  146. TokenAuth::clearToken($uid, $type, $token);
  147. }
  148. }
  149. /**
  150. * 解析token
  151. * @param string|null $token
  152. * @return array
  153. */
  154. public function parseToken(?string $token)
  155. {
  156. if (empty($token)) {
  157. //定义专属于授权认证机制的错误响应, 定义专属语言包
  158. throw new AuthException('MUST_LOGIN', 401);
  159. }
  160. //暴力操作,截停所有异常覆盖为token失效
  161. try {
  162. $token_info = TokenAuth::parseToken($token, AppTypeDict::ADMIN);
  163. } catch ( Throwable $e ) {
  164. // if(env('app_debug', false)){
  165. // throw new AuthException($e->getMessage(), 401);
  166. // }else{
  167. throw new AuthException('LOGIN_EXPIRE', 401);
  168. // }
  169. }
  170. if (!$token_info) {
  171. throw new AuthException('MUST_LOGIN', 401);
  172. }
  173. //验证有效次数或过期时间
  174. return $token_info;
  175. }
  176. /**
  177. * 重置管理员密码
  178. * @return void
  179. */
  180. public static function resetAdministratorPassword(int|string $password = '123456') {
  181. $super_admin_uid = ( new SysUserRole() )->where([
  182. [ 'site_id', '=', request()->defaultSiteId() ],
  183. [ 'is_admin', '=', 1 ]
  184. ])->value('uid');
  185. $user = (new UserService())->find($super_admin_uid);
  186. $user->password = create_password($password);
  187. $user->save();
  188. self::clearToken($super_admin_uid);
  189. }
  190. }