Skip to content

Commit

Permalink
add file log
Browse files Browse the repository at this point in the history
  • Loading branch information
Mario Moreno committed Aug 27, 2023
1 parent 4955b8a commit 9ee6b88
Show file tree
Hide file tree
Showing 10 changed files with 101 additions and 20 deletions.
4 changes: 4 additions & 0 deletions .env
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
TZ=America/Buenos_Aires

LOG_FILE_PATH=./logs/app.log
LOG_FILE_ENABLED=false
4 changes: 4 additions & 0 deletions .env.example
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
TZ=UTC

LOG_FILE_PATH=./logs/app.log
LOG_FILE_ENABLED=false
14 changes: 14 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,20 @@ Logger global interceptor library for Nest apps
$ npm install @mariomorenodev/nest-response-logger
```

Copy the variables from the `.env.example` file to the `.env` file

```bash
$ cp .env.example .env
```

Or add variables to the environment

```bash
TZ=America/Buenos_Aires

LOG_FILE_PATH=./logs/app.log
LOG_FILE_ENABLED=false
```
## Usage

Add the NestResponseLogger service globally in the `main.ts` file:
Expand Down
3 changes: 2 additions & 1 deletion libs/nest-response-logger/package.json
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"name": "@mariomorenodev/nest-response-logger",
"version": "1.0.7",
"version": "1.0.8",
"description": "Logger global interceptor library for Nest apps",
"main": "dist/index.js",
"types": "dist/index.d.ts",
Expand All @@ -26,6 +26,7 @@
"@nestjs/core": "^10.0.0",
"@nestjs/platform-express": "^10.0.0",
"moment": "^2.29.4",
"moment-timezone": "^0.5.43",
"reflect-metadata": "^0.1.13",
"rxjs": "^7.8.1"
},
Expand Down
7 changes: 3 additions & 4 deletions libs/nest-response-logger/src/logger.interceptor.spec.ts
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,7 @@ describe('LoggerInterceptor', () => {
jest.clearAllMocks();
});

it('Registrar log cuando la respuesta es correcta y enableLog es verdadero', async () => {
it('Record log when response is correct and enableLog is true', async () => {
const value = { enableLog: true };
const context = createMockContext(HttpStatus.OK);
const next = createMockNext({ enableLog: true });
Expand All @@ -31,7 +31,7 @@ describe('LoggerInterceptor', () => {
expect(result).toEqual(value);
});

it('No Registrar log cuando la respuesta es correcta y enableLog es falso', async () => {
it('Don not log when response is correct and enableLog log es false', async () => {
const value = { enableLog: false };
const context = createMockContext(HttpStatus.OK);
const next = createMockNext({ enableLog: false });
Expand All @@ -43,7 +43,7 @@ describe('LoggerInterceptor', () => {
expect(result).toEqual(value);
});

it('Registrar log cuando la respuesta es de error', async () => {
it('Record log when response is error', async () => {
const value = new HttpException('Internal server error', HttpStatus.OK);
const context = createMockContext(HttpStatus.OK);
const next = createMockNext(
Expand All @@ -57,7 +57,6 @@ describe('LoggerInterceptor', () => {
expect(result).toEqual(value);
});

// Funciones de utilidad para crear objetos simulados
function createMockContext(statusCode: number): ExecutionContext {
return {
switchToHttp: () => ({
Expand Down
2 changes: 1 addition & 1 deletion libs/nest-response-logger/src/logger.interceptor.ts
Original file line number Diff line number Diff line change
Expand Up @@ -43,7 +43,7 @@ export class LoggerInterceptor implements NestInterceptor {
}),
// Maneja el error capturado en el servicio si ocurre y registrarlo en los logs
catchError((error) => {
const statusCode: number = error.getStatus() ?? 500;
const statusCode: number = error.getStatus ? error.getStatus() : 500;
const message = error.message ?? 'Internal server error';
const stack = error.stack ?? 'No stack trace';

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,7 @@ describe('NestResponseLoggerService', () => {
jest.clearAllMocks();
});

it('Registrar logger console log', () => {
it('Log logger console log', () => {
const message = 'This is a log message';
const logSpy = jest.spyOn(console, 'log');

Expand All @@ -31,7 +31,7 @@ describe('NestResponseLoggerService', () => {
);
});

it('Registrar logger console error', () => {
it('Log logger console error', () => {
const message = 'This is a error message';
const errorSpy = jest.spyOn(console, 'error');

Expand All @@ -44,7 +44,7 @@ describe('NestResponseLoggerService', () => {
);
});

it('Registrar logger console warn', () => {
it('Log logger console warn', () => {
const message = 'This is a warn message';
const warnSpy = jest.spyOn(console, 'warn');

Expand All @@ -57,7 +57,7 @@ describe('NestResponseLoggerService', () => {
);
});

it('Registrar logger console debug', () => {
it('Log logger console debug', () => {
const message = 'This is a debug message';
const debugSpy = jest.spyOn(console, 'debug');

Expand Down
52 changes: 45 additions & 7 deletions libs/nest-response-logger/src/nest-response-logger.service.ts
Original file line number Diff line number Diff line change
@@ -1,30 +1,68 @@
import { Injectable, LoggerService } from '@nestjs/common';
import 'moment-timezone';
import * as moment from 'moment';
import { existsSync, mkdirSync, appendFileSync } from 'fs';

@Injectable()
export class NestResponseLoggerService implements LoggerService {
private now: string;
private timezone: string;
private readonly logFilePath: string;
private readonly logFileEnabled: string;

constructor() {
this.now = moment(new Date()).format('DD/MM/YYYY HH:mm:ss');
this.timezone = process.env.TZ || 'UTC';
this.logFilePath = process.env.LOG_FILE_PATH || './logs/app.log';
this.logFileEnabled = process.env.LOG_FILE_ENABLED || 'false';
this.ensureLogDirectoryExists();
}

log(message: any, ...optionalParams: any[]) {
console.log(`[${this.now}] [LOG] ${message}`, optionalParams);
const now = this.getCurrentTime();
console.log(`[${now}] [LOG] ${message}`, optionalParams);
this.writeToFile(`[${now}] [LOG] ${message} ${optionalParams}`);
}

error(message: any, ...optionalParams: any[]) {
console.error(`[${this.now}] [ERROR] ${message}`, optionalParams);
const now = this.getCurrentTime();
console.error(`[${now}] [ERROR] ${message}`, optionalParams);
this.writeToFile(`[${now}] [LOG] ${message} ${optionalParams}`);
}

warn(message: any, ...optionalParams: any[]) {
console.warn(`[${this.now}] [WARN] ${message}`, optionalParams);
const now = this.getCurrentTime();
console.warn(`[${now}] [WARN] ${message}`, optionalParams);
this.writeToFile(`[${now}] [LOG] ${message} ${optionalParams}`);
}

debug?(message: any, ...optionalParams: any[]) {
console.debug(`[${this.now}] [DEBUG] ${message}`, optionalParams);
const now = this.getCurrentTime();
console.debug(`[${now}] [DEBUG] ${message}`, optionalParams);
this.writeToFile(`[${now}] [LOG] ${message} ${optionalParams}`);
}

verbose?(message: any, ...optionalParams: any[]) {
console.info(`[${this.now}] [VERBOSE] ${message}`, optionalParams);
const now = this.getCurrentTime();
console.info(`[${now}] [VERBOSE] ${message}`, optionalParams);
this.writeToFile(`[${now}] [LOG] ${message} ${optionalParams}`);
}

private getCurrentTime(): string {
return moment().tz(this.timezone).format('DD/MM/YYYY HH:mm:ss');
}

private ensureLogDirectoryExists(): void {
const logDirectory = this.logFilePath.substring(
0,
this.logFilePath.lastIndexOf('/'),
);
if (!existsSync(logDirectory)) {
mkdirSync(logDirectory, { recursive: true });
}
}

private writeToFile(log: string): void {
if (this.logFileEnabled === 'true') {
appendFileSync(this.logFilePath, log + '\n', 'utf8');
}
}
}
24 changes: 22 additions & 2 deletions package-lock.json

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

3 changes: 2 additions & 1 deletion package.json
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"name": "response-logger-library",
"version": "1.0.7",
"version": "1.0.8",
"description": "",
"author": "",
"private": true,
Expand All @@ -26,6 +26,7 @@
"@nestjs/core": "^10.0.0",
"@nestjs/platform-express": "^10.0.0",
"moment": "^2.29.4",
"moment-timezone": "^0.5.43",
"reflect-metadata": "^0.1.13",
"rxjs": "^7.8.1"
},
Expand Down

0 comments on commit 9ee6b88

Please sign in to comment.