Compare commits

...

4 Commits

9 changed files with 1323 additions and 3369 deletions

View File

@ -31,6 +31,7 @@
"@nestjs/platform-express": "^10.0.0",
"@nestjs/swagger": "^7.3.1",
"@nestjs/typeorm": "^10.0.2",
"@sendgrid/mail": "^8.1.3",
"argon2": "^0.40.1",
"class-transformer": "^0.5.1",
"class-validator": "^0.14.1",

File diff suppressed because it is too large Load Diff

View File

@ -10,6 +10,7 @@ import { SecurityHeadersMiddleware } from './middleware/security-middleware/secu
import { AuthModule } from './modules/auth-module/auth.module';
import { AccessTokenGuard } from './modules/auth-module/common/guards';
import { DatabaseModule } from './modules/database-module/database.module';
import { SendgridModule } from './modules/sendgrid-module/sendgrid.module';
import { UserModule } from './modules/user-module/user.module';
@Module({
@ -20,6 +21,7 @@ import { UserModule } from './modules/user-module/user.module';
DatabaseModule,
AuthModule,
UserModule,
SendgridModule,
],
controllers: [AppController],
providers: [AppService, { provide: 'APP_GUARD', useClass: AccessTokenGuard }],

View File

@ -3,6 +3,7 @@ import { JwtModule } from '@nestjs/jwt';
import { TypeOrmModule } from '@nestjs/typeorm';
import { UserCredentials } from 'src/entities';
import { SendgridModule } from '../sendgrid-module/sendgrid.module';
import { UserModule } from '../user-module/user.module';
import { AuthController } from './controller/auth.controller';
@ -15,6 +16,7 @@ import { AccessTokenStrategy, RefreshTokenStrategy } from './strategies';
@Module({
imports: [
UserModule,
SendgridModule,
JwtModule.register({}),
TypeOrmModule.forFeature([UserCredentials]),
],

View File

@ -1,5 +1,6 @@
import { ForbiddenException, Injectable } from '@nestjs/common';
import { PasswordConfirmationMailService } from '../../sendgrid-module/services/password-confirmation.mail.service';
import { UserDataRepository } from '../../user-module/repositories/user-data.repository';
import { TokensDto, UserCredentialsDto } from '../models/dto';
import { UserCredentialsRepository } from '../repositories/user-credentials.repository';
@ -13,7 +14,8 @@ export class AuthService {
private readonly userCredentialsRepository: UserCredentialsRepository,
private readonly userDataRepository: UserDataRepository,
private readonly tokenManagementService: TokenManagementService,
private readonly encryptionService: EncryptionService
private readonly encryptionService: EncryptionService,
private readonly passwordConfirmationMailService: PasswordConfirmationMailService
) {}
public async signup(userCredentials: UserCredentialsDto): Promise<TokensDto> {
@ -27,6 +29,11 @@ export class AuthService {
await this.userDataRepository.createInitialUserData(user);
// TODO Send email confirmation
// await this.passwordConfirmationMailService.sendPasswordConfirmationMail(
// user.email
// );
return this.generateAndPersistTokens(user.id, user.email);
}

View File

@ -0,0 +1,22 @@
import { Module } from '@nestjs/common';
import { ConfigModule, ConfigService } from '@nestjs/config';
import { PasswordConfirmationMailService } from './services/password-confirmation.mail.service';
import { TemplateConfigService } from './services/template-config.service';
@Module({
imports: [ConfigModule],
providers: [
{
provide: 'SEND_GRID_API_KEY',
useFactory: (configService: ConfigService): string =>
configService.get<string>('SEND_GRID_API_KEY'),
inject: [ConfigService],
},
PasswordConfirmationMailService,
TemplateConfigService,
],
controllers: [],
exports: [PasswordConfirmationMailService],
})
export class SendgridModule {}

View File

@ -0,0 +1,19 @@
import { Inject, Injectable } from '@nestjs/common';
import * as SendGridMailApi from '@sendgrid/mail';
// API: https://www.twilio.com/docs/sendgrid/api-reference/mail-send/mail-send#request-body
@Injectable()
export abstract class BaseMailService {
public constructor(
@Inject('SEND_GRID_API_KEY') protected readonly sendGridApiKey: string
) {
SendGridMailApi.setApiKey(this.sendGridApiKey);
}
protected async sendMail(
mailOptions: SendGridMailApi.MailDataRequired
): Promise<[SendGridMailApi.ClientResponse, object]> {
return SendGridMailApi.send(mailOptions);
}
}

View File

@ -0,0 +1,36 @@
import { Inject, Injectable } from '@nestjs/common';
import * as SendGridMailApi from '@sendgrid/mail';
import { BaseMailService } from './base.mail.service';
import { TemplateConfigService } from './template-config.service';
@Injectable()
export class PasswordConfirmationMailService extends BaseMailService {
private readonly PASSWORD_CONFIRMATION_EMAIL: string =
'PASSWORD_CONFIRMATION_EMAIL';
public constructor(
@Inject('SEND_GRID_API_KEY') protected readonly sendGridApiKey: string,
private readonly templateConfigService: TemplateConfigService
) {
super(sendGridApiKey);
}
public async sendPasswordConfirmationMail(to: string): Promise<void> {
const templateId: string = this.templateConfigService.getTemplateId(
this.PASSWORD_CONFIRMATION_EMAIL
);
const mailoptions: SendGridMailApi.MailDataRequired = {
to,
from: { email: 'info@igor-propisnov.com', name: 'Ticket App' },
templateId: templateId,
dynamicTemplateData: {
name: 'Mara',
buttonUrl: 'https://igor-propisnov.com',
},
};
await this.sendMail(mailoptions);
}
}

View File

@ -0,0 +1,11 @@
import { Injectable } from '@nestjs/common';
import { ConfigService } from '@nestjs/config';
@Injectable()
export class TemplateConfigService {
public constructor(private configService: ConfigService) {}
public getTemplateId(key: string): string {
return this.configService.get<string>(`SENDGRID_TEMPLATE_${key}`);
}
}