11import { HttpException , HttpStatus , Injectable } from '@nestjs/common' ;
2+ import { ConfigService } from '@nestjs/config' ;
23import { InjectRepository } from '@nestjs/typeorm' ;
34import { LoggerService } from '@src/plugin/logger/logger.service' ;
45import { RedisService } from '@src/plugin/redis/redis.service' ;
56import { ToolsService } from '@src/plugin/tools/tools.service' ;
67import { Repository , SelectQueryBuilder } from 'typeorm' ;
78import { AccountEntity } from '../account/entities/account.entity' ;
89import { LoginDto } from './dto/login.dto' ;
9- import { LoginVo } from './vo/login.vo' ;
10-
11- type findAccountType = Omit < AccountEntity , 'created_at' | 'updated_at' > ;
10+ import { LoginAccountVo , LoginTokenDataVo , LoginVo } from './vo/login.vo' ;
1211
1312@Injectable ( )
1413export class LoginService {
@@ -17,7 +16,8 @@ export class LoginService {
1716 private readonly accountRepository : Repository < AccountEntity > ,
1817 private readonly toolsService : ToolsService ,
1918 private readonly loggerService : LoggerService ,
20- private readonly redisService : RedisService
19+ private readonly redisService : RedisService ,
20+ private readonly configService : ConfigService
2121 ) { }
2222
2323 /**
@@ -30,32 +30,15 @@ export class LoginService {
3030 */
3131 async loginApi ( req : LoginDto ) : Promise < LoginVo > {
3232 const { username, password } = req ;
33- const accountEntity :
34- | Pick < AccountEntity , 'id' | 'username' | 'status' | 'accountType' | 'password' | 'salt' >
35- | undefined = await this . queryLoginBuilder
33+ const accountEntity : LoginAccountVo | undefined = await this . queryLoginBuilder
3634 . where ( '(account.username = :username)' , { username : username } )
3735 . getRawOne ( ) ;
3836 if ( accountEntity ?. id ) {
3937 console . log ( accountEntity . password , '111' , password ) ;
4038 // 判断密码是否正确
4139 const saltPassword = this . toolsService . makePassword ( password , accountEntity . salt ) ;
4240 if ( Object . is ( saltPassword , accountEntity . password ) ) {
43- // 生成token存储到token表中并且返回给前端
44- const token = this . toolsService . uuidToken ;
45- // 根据资源id获取资源信息
46- this . redisService . set (
47- token ,
48- {
49- userInfo : accountEntity , // 用户信息
50- } ,
51- 7 * 24 * 60 * 60
52- ) ;
53- return {
54- id : accountEntity . id , // 账号id
55- username : accountEntity . username , // 用户名
56- accountType : accountEntity . accountType , // 账号类型:0普通账号,1是主账号,2是超管
57- token, // 登录的token
58- } ;
41+ return await this . generateToken ( accountEntity ) ;
5942 } else {
6043 throw new HttpException ( '账号或密码错误' , HttpStatus . OK ) ;
6144 }
@@ -65,15 +48,35 @@ export class LoginService {
6548 }
6649 }
6750
51+ /**
52+ * @Author : 水痕
53+ * @Date : 2023-10-08 08:44:55
54+ * @LastEditors : 水痕
55+ * @Description :
56+ * @param {string } token
57+ * @return {* }
58+ */
59+ async refreshTokenApi ( token : string ) : Promise < LoginVo > {
60+ // 1.在redis中读取是否有这个token
61+ const redisData = await this . redisService . get ( token ) ;
62+ if ( redisData ) {
63+ const redisDataObj = redisData as unknown as LoginTokenDataVo ;
64+ return await this . generateToken ( redisDataObj . userInfo ) ;
65+ } else {
66+ throw new HttpException (
67+ JSON . stringify ( { code : 10024 , message : '你还没登录,请先登录' } ) ,
68+ HttpStatus . OK
69+ ) ;
70+ }
71+ }
6872 /**
6973 * @Author :
7074 * @Date : 2023-10-08 07:52:37
7175 * @LastEditors :
7276 * @Description : 内部使用查询数据
7377 * @return {* }
7478 */
75-
76- private get queryLoginBuilder ( ) : SelectQueryBuilder < findAccountType > {
79+ private get queryLoginBuilder ( ) : SelectQueryBuilder < LoginAccountVo > {
7780 return this . accountRepository
7881 . createQueryBuilder ( 'account' )
7982 . select ( 'account.id' , 'id' )
@@ -83,4 +86,52 @@ export class LoginService {
8386 . addSelect ( 'account.password' , 'password' )
8487 . addSelect ( 'account.salt' , 'salt' ) ;
8588 }
89+
90+ /**
91+ * @Author : 水痕
92+ * @Date : 2023-10-08 09:07:02
93+ * @LastEditors : 水痕
94+ * @Description : 内部生成token
95+ * @param {LoginAccountVo } accountEntity
96+ * @return {* }
97+ */
98+ private async generateToken (
99+ accountEntity : LoginAccountVo
100+ ) : Promise < Promise < Promise < Promise < LoginVo > > > > {
101+ // 生成token存储到token表中并且返回给前端
102+ const tokenExpire : number = this . configService . get ( 'tokenExpire' ) ?? 2 ;
103+ const refreshTokenExpire : number = this . configService . get ( 'refreshTokenExpire' ) ?? 7 ;
104+ const token = this . toolsService . uuidToken ;
105+ const refreshToken = this . toolsService . uuidToken ;
106+ const sign = this . toolsService . uuidToken ;
107+ // 根据资源id获取资源信息
108+ const redisData : LoginTokenDataVo = {
109+ userInfo : accountEntity , // 用户信息
110+ sign,
111+ } ;
112+ // 正常token
113+ await this . redisService . set ( token , redisData , tokenExpire * 60 * 60 ) ;
114+ // 刷新token
115+ await this . redisService . set ( refreshToken , redisData , refreshTokenExpire * 24 * 60 * 60 ) ;
116+ // 删除redis中历史的token,并且设置新的
117+ const accountTokenKey = this . toolsService . generateLoginTokenKey ( accountEntity . id ) ;
118+ const accountRefreshTokenKey = this . toolsService . generateLoginRefreshTokenKey ( accountEntity . id ) ;
119+ const accountToken = ( await this . redisService . get ( accountTokenKey ) ) as unknown as string ;
120+ const accountRefreshToken = ( await this . redisService . get (
121+ accountRefreshTokenKey
122+ ) ) as unknown as string ;
123+ console . log ( accountToken , accountRefreshToken , '要删除的' ) ;
124+ await this . redisService . del ( accountToken ) ;
125+ await this . redisService . del ( accountRefreshToken ) ;
126+ this . redisService . set ( accountTokenKey , token , tokenExpire * 60 * 60 ) ;
127+ this . redisService . set ( accountRefreshTokenKey , refreshToken , refreshTokenExpire * 24 * 60 * 60 ) ;
128+ return {
129+ id : accountEntity . id , // 账号id
130+ username : accountEntity . username , // 用户名
131+ accountType : accountEntity . accountType , // 账号类型:0普通账号,1是主账号,2是超管
132+ token, // 登录的token
133+ refreshToken,
134+ sign,
135+ } ;
136+ }
86137}
0 commit comments