11. Nest.js 광부왕 게임 서버 Log 저장 모듈 생성
2023. 3. 13. 17:09ㆍ프로젝트/게임 서버 - Nest.js
로그 저장은 account, stage, item, company 분류
account : 계정 로그인 관련 로그
stage : 진행 게임 관련 로그
item : 아이탬 관련 로그
company : 회사 (길드) 관련 로그
1. 모듈 생성 ( Mongoose 설정 ), dayjs 설치
명령어 작성
nest g mo logs
npm i dayjs
src/logs/logs.module.ts 파일에서 MongooseModule 의존성 주입한다.
import { Module } from '@nestjs/common';
import { MongooseModule } from '@nestjs/mongoose';
import { Logs, LogsSchema } from '../model/logs.model';
@Module({
imports: [
MongooseModule.forFeature([
{
name: Logs.name,
schema: LogsSchema,
},
]),
],
providers: [],
controllers: [],
exports: [],
})
export class LogsModule {}
2. DTO 생성
logs.dto.ts 파일에 두개의 DTO를 작성한다.
- 로그 찾기 DTO
import { ApiProperty } from '@nestjs/swagger';
import { IsIn } from 'class-validator';
import { IsNotEmpty, IsString, Matches } from 'class-validator';
export class FindLogDto {
@ApiProperty({
example: 'stage',
description: 'type',
required: true,
})
@IsIn(['account', 'stage', 'item', 'company'])
@IsNotEmpty()
type: 'account' | 'stage' | 'item' | 'company';
@ApiProperty({
example: '2022-01-01',
description: 'startDate',
required: true,
})
@IsString()
@IsNotEmpty()
@Matches(/^\d{4}-(0[1-9]|1[012])-(0[1-9]|[12][0-9]|3[01])$/)
startDate: string;
@ApiProperty({
example: '2022-01-10',
description: 'endDate',
required: true,
})
@IsString()
@IsNotEmpty()
@Matches(/^\d{4}-(0[1-9]|1[012])-(0[1-9]|[12][0-9]|3[01])$/)
endDate: string;
}
- 로그 저장 DTO
export class SaveLogDto {
@IsIn(['account', 'stage', 'item', 'company'])
@IsNotEmpty()
type: 'account' | 'stage' | 'item' | 'company';
log: any;
}
3. Controller 생성
명령어 작성
nest g co logs
src/logs/logs.controller.ts 파일 수정
* 로그 저장은 따로 API통신으로 저장 되지 않고 서버에서 저장하기 때문에 findLog() 함수만 있다.
import { Controller } from '@nestjs/common';
import { Get, Param } from '@nestjs/common';
import { FindLogDto } from './dto/logs.dto';
import { LogsService } from './logs.service';
@Controller('logs')
export class LogsController {
constructor(private readonly logsService: LogsService) {}
@Get('/:type/:startDate/:endDate')
async findLog(@Param() param: FindLogDto) {
return await this.logsService.findLog(param);
}
}
4. Service 생성
명령어 작성
nest g s logs
src/logs/logs.service.ts 파일 수정
* 서버 시간 (UTC + 0)을 한국시간(UTC + 9)으로 시간을 맞추었다.
import { Injectable } from '@nestjs/common';
import dayjs from 'dayjs';
import { FindLogDto, SaveLogDto } from './dto/logs.dto';
import { LogRepository } from './logs.repository';
@Injectable()
export class LogsService {
constructor(private readonly logRepository: LogRepository) {}
async findLog(data: FindLogDto) {
const { type, startDate, endDate } = data;
const start = dayjs(new Date(startDate))
.subtract(1, 'day')
.set('hours', 5)
.set('minutes', 0)
.set('seconds', 0)
.toDate();
const end = dayjs(new Date(endDate))
.set('hours', 15)
.set('minutes', 0)
.set('seconds', 0)
.toDate();
const log = await this.logRepository.findLog({ type, start, end });
return log;
}
async saveLog(user: string, data: SaveLogDto) {
await this.logRepository.saveLog(user, data);
}
}
5. Repository 생성
src/logs/logs.repository.ts 파일 생성 후 작성
import { Injectable } from '@nestjs/common';
import { InjectModel } from '@nestjs/mongoose';
import dayjs from 'dayjs';
import { Model } from 'mongoose';
import { Logs } from '../model/logs.model';
import { SaveLogDto } from './dto/logs.dto';
@Injectable()
export class LogRepository {
constructor(@InjectModel(Logs.name) private readonly logModel: Model<Logs>) {}
async findLog(data: { type: string; start: Date; end: Date }) {
const { type, start, end } = data;
return await this.logModel
.find()
.select({ [`${type}Log`]: 1, user: 1 })
.gte('createdAt', start)
.lte('createdAt', end);
}
async saveLog(user: string, data: SaveLogDto) {
const { type, log } = data;
const now = new Date();
const date = dayjs(now).format('YYYY-MM-DD');
const savedLog = await this.logModel.findOne({ user, date });
log.time = new Date();
if (savedLog) {
await this.logModel.findOneAndUpdate(
{ _id: savedLog._id },
{ $push: { [`${type}Log`]: log } },
);
} else {
await this.logModel.create({ user, date, [`${type}Log`]: [log] });
}
}
}
6. 모듈 설정
* 로그 저장을 다른 모듈에서 재사용 하기 위해 LogsService은 exports에 넣는다.
import { Module } from '@nestjs/common';
import { LogRepository } from './logs.repository';
import { LogsService } from './logs.service';
import { LogsController } from './logs.controller';
import { MongooseModule } from '@nestjs/mongoose';
import { Logs, LogsSchema } from '../model/logs.model';
@Module({
imports: [
MongooseModule.forFeature([
{
name: Logs.name,
schema: LogsSchema,
},
]),
],
providers: [LogsService, LogRepository],
controllers: [LogsController],
exports: [LogsService],
})
export class LogsModule {}
728x90
반응형
'프로젝트 > 게임 서버 - Nest.js' 카테고리의 다른 글
10. Nest.js 광부왕 게임 서버 Socket.IO 설정 (0) | 2023.03.04 |
---|---|
9. Nest.js 광부왕 게임 서버 Decorator 생성 (0) | 2023.03.03 |
8. Nest.js 광부왕 게임 서버 JWT 설정 (0) | 2023.03.03 |
7. Nest.js 광부왕 게임 서버 Interceptor 적용 (0) | 2023.03.03 |
6. Nest.js 광부왕 게임 서버 Filter 적용 (0) | 2023.03.03 |