@@ -12,13 +12,14 @@ import { faker } from '@faker-js/faker';
1212import * as crypto from 'crypto' ;
1313import { v4 as uuid } from 'uuid' ;
1414import * as bcrypt from 'bcryptjs' ;
15- import { AuthEmailLoginDto , LoginResponseDto } from './dtos' ;
15+ import { AuthEmailLoginDto , AuthUpdateDto , LoginResponseDto } from './dtos' ;
1616import { convertTimeString } from 'convert-time-string' ;
1717import { RedisService } from '~/common/redis' ;
1818import { PREFIX_REVOKE_ACCESS_TOKEN , PREFIX_REVOKE_REFRESH_TOKEN } from './auth.constant' ;
1919import { JwtPayloadType , JwtRefreshPayloadType } from './strategies/types' ;
2020import { Session , SessionService } from '~/modules/session' ;
2121import { MailService } from '~/modules/mail' ;
22+ import { GhnService } from '~/third-party' ;
2223
2324@Injectable ( )
2425export class AuthService {
@@ -30,6 +31,7 @@ export class AuthService {
3031 private readonly mailService : MailService ,
3132 private readonly redisService : RedisService ,
3233 private readonly sessionService : SessionService ,
34+ private readonly ghnService : GhnService ,
3335 ) { }
3436
3537 async register ( dto : AuthSignupDto ) : Promise < void > {
@@ -512,6 +514,120 @@ export class AuthService {
512514 ] ) ;
513515 }
514516
517+ async update (
518+ userJwtPayload : JwtPayloadType ,
519+ userDto : AuthUpdateDto ,
520+ ) : Promise < NullableType < User > > {
521+ const userData = userDto ;
522+ if ( userData ?. userName ) {
523+ const user = await this . usersService . findByUserName ( userData . userName ) ;
524+ if ( user ) {
525+ throw new HttpException (
526+ {
527+ status : HttpStatus . UNPROCESSABLE_ENTITY ,
528+ errors : {
529+ userName : 'userNameAlreadyExists' ,
530+ } ,
531+ } ,
532+ HttpStatus . UNPROCESSABLE_ENTITY ,
533+ ) ;
534+ }
535+ }
536+
537+ if ( userData . password ) {
538+ if ( ! userData . oldPassword ) {
539+ throw new HttpException (
540+ {
541+ status : HttpStatus . UNPROCESSABLE_ENTITY ,
542+ errors : {
543+ oldPassword : 'missingOldPassword' ,
544+ } ,
545+ } ,
546+ HttpStatus . UNPROCESSABLE_ENTITY ,
547+ ) ;
548+ }
549+
550+ const currentUser = await this . usersService . findById ( userJwtPayload . userId ) ;
551+
552+ if ( ! currentUser ) {
553+ throw new HttpException (
554+ {
555+ status : HttpStatus . UNPROCESSABLE_ENTITY ,
556+ errors : {
557+ user : 'userNotFound' ,
558+ } ,
559+ } ,
560+ HttpStatus . UNPROCESSABLE_ENTITY ,
561+ ) ;
562+ }
563+
564+ if ( ! currentUser . password ) {
565+ throw new HttpException (
566+ {
567+ status : HttpStatus . UNPROCESSABLE_ENTITY ,
568+ errors : {
569+ oldPassword : 'incorrectOldPassword' ,
570+ } ,
571+ } ,
572+ HttpStatus . UNPROCESSABLE_ENTITY ,
573+ ) ;
574+ }
575+
576+ const isValidOldPassword = await bcrypt . compare (
577+ userData . oldPassword ,
578+ currentUser . password ,
579+ ) ;
580+
581+ if ( ! isValidOldPassword ) {
582+ throw new HttpException (
583+ {
584+ status : HttpStatus . UNPROCESSABLE_ENTITY ,
585+ errors : {
586+ oldPassword : 'incorrectOldPassword' ,
587+ } ,
588+ } ,
589+ HttpStatus . UNPROCESSABLE_ENTITY ,
590+ ) ;
591+ } else {
592+ await this . sessionService . softDelete ( {
593+ user : {
594+ _id : currentUser . _id ,
595+ } ,
596+ excludeId : userJwtPayload . sessionId ,
597+ } ) ;
598+ }
599+ }
600+
601+ if ( userData ?. address !== null || userData ?. address !== undefined ) {
602+ if ( userData . address ?. length === 0 ) {
603+ userData . address = [ ] ;
604+ } else {
605+ const addressPromises = userData . address ?. map ( ( address ) =>
606+ this . ghnService . getSelectedAddress ( address ) ,
607+ ) ;
608+
609+ try {
610+ await Promise . all ( addressPromises ?? [ ] ) ;
611+ } catch ( error ) {
612+ throw new HttpException (
613+ {
614+ status : HttpStatus . UNPROCESSABLE_ENTITY ,
615+ errors : {
616+ address : 'invalidAddress' ,
617+ message : error . message ,
618+ } ,
619+ } ,
620+ HttpStatus . UNPROCESSABLE_ENTITY ,
621+ ) ;
622+ }
623+ }
624+ }
625+
626+ await this . usersService . update ( userJwtPayload . userId , userData ) ;
627+
628+ return new User ( await this . usersService . findById ( userJwtPayload . userId ) ) ;
629+ }
630+
515631 private async getTokensData ( data : {
516632 userId : User [ '_id' ] ;
517633 role : User [ 'role' ] ;
0 commit comments