diff --git a/README.md b/README.md index 6df43d2..3606423 100644 --- a/README.md +++ b/README.md @@ -4,7 +4,6 @@ [![Snyk Security Scan](https://github.com/SkinSightYnov/backend/actions/workflows/snyk.yml/badge.svg)](https://github.com/SkinSightYnov/backend/actions/workflows/snyk.yml) - ## Description ... @@ -13,6 +12,9 @@ ```bash $ npm install + +$ npx prisma generate : génération des types + ``` ## Running the app diff --git a/package.json b/package.json index b79c4ba..5db5f38 100644 --- a/package.json +++ b/package.json @@ -30,11 +30,13 @@ "@nestjs/platform-express": "^10.0.0", "@nestjs/swagger": "^7.1.17", "@nestjs/terminus": "^10.2.0", + "@nestjs/throttler": "^5.1.2", "@prisma/client": "^5.9.0", "axios": "^1.6.5", "bcrypt": "^5.1.1", "class-transformer": "^0.5.1", "class-validator": "^0.14.1", + "helmet": "^7.1.0", "passport": "^0.7.0", "passport-jwt": "^4.0.1", "prom-client": "^15.1.0", diff --git a/src/app.module.ts b/src/app.module.ts index b0d6b5b..70b993c 100644 --- a/src/app.module.ts +++ b/src/app.module.ts @@ -4,7 +4,7 @@ import { AppService } from './app.service'; import { HealthModule } from './prisma/health/health.module'; import { LoggerModule } from './logger/logger.module'; import { MetricModule } from './metric/metric.module'; -import { APP_INTERCEPTOR } from '@nestjs/core'; +import { APP_GUARD, APP_INTERCEPTOR } from '@nestjs/core'; import { LoggingInterceptor } from './logger/logger.interceptor'; import { ConfigModule } from '@nestjs/config'; import { AuthModule } from './auth/auth.module'; @@ -15,9 +15,16 @@ import { MedecinsModule } from './medecins/medecins.module'; import { DermatologuesModule } from './dermatologues/dermatologues.module'; import { AppointmentsModule } from './appointments/appointments.module'; import { PatientsModule } from './patients/patients.module'; +import { ThrottlerGuard, ThrottlerModule } from '@nestjs/throttler'; @Module({ imports: [ + ThrottlerModule.forRoot([ + { + ttl: 60000, + limit: 150, + }, + ]), UsersModule, HealthModule, LoggerModule, @@ -39,6 +46,10 @@ import { PatientsModule } from './patients/patients.module'; provide: APP_INTERCEPTOR, useClass: LoggingInterceptor, }, + { + provide: APP_GUARD, + useClass: ThrottlerGuard, + }, ], }) export class AppModule {} diff --git a/src/main.ts b/src/main.ts index 1d306d4..9275610 100644 --- a/src/main.ts +++ b/src/main.ts @@ -4,6 +4,7 @@ import { AppModule } from './app.module'; import { LoggingInterceptor } from './logger/logger.interceptor'; import { ValidationPipe, ClassSerializerInterceptor } from '@nestjs/common'; import { SanitizerGuard } from './sanitizer.guard'; +import helmet from 'helmet'; declare const module: any; async function bootstrap() { @@ -11,6 +12,7 @@ async function bootstrap() { app.enableCors({ origin: '*' }); app.useGlobalInterceptors(new LoggingInterceptor()); app.useGlobalGuards(new SanitizerGuard()); + app.use(helmet()); app.useGlobalPipes(new ValidationPipe({ whitelist: true })); app.useGlobalInterceptors(new ClassSerializerInterceptor(app.get(Reflector))); diff --git a/src/sanitizer.guard.ts b/src/sanitizer.guard.ts index 19f1377..87599d5 100644 --- a/src/sanitizer.guard.ts +++ b/src/sanitizer.guard.ts @@ -1,35 +1,27 @@ -import { CanActivate, ExecutionContext, Injectable } from '@nestjs/common'; -import { Observable } from 'rxjs'; -import xss from 'xss'; +import { Injectable, CanActivate, ExecutionContext } from '@nestjs/common'; +import * as xss from 'xss'; @Injectable() export class SanitizerGuard implements CanActivate { - canActivate( - context: ExecutionContext, - ): boolean | Promise | Observable { + canActivate(context: ExecutionContext): boolean { const request = context.switchToHttp().getRequest(); if (request.body) { - request.body = this.cleanData(request.body); - } - - if (request.query) { - request.query = this.cleanData(request.query); - } - - if (request.params) { - request.params = this.cleanData(request.params); + this.sanitizeData(request.body); } return true; } - private cleanData(data: Record): Record { + + private sanitizeData(data: Record): void { for (const key in data) { - if (data.hasOwnProperty(key) && typeof data[key] === 'string') { - data[key] = xss(data[key]); + if (data.hasOwnProperty(key)) { + if (typeof data[key] === 'string') { + data[key] = xss.filterXSS(data[key]); + } else if (typeof data[key] === 'object') { + this.sanitizeData(data[key]); + } } } - - return data; } }