From 95bfa31509403f35c253a7fe7ee059c21d12920f Mon Sep 17 00:00:00 2001 From: YangGwangSeong Date: Sun, 24 Nov 2024 19:38:25 +0900 Subject: [PATCH] =?UTF-8?q?:sparkles:=20feat:=20=EB=AA=A8=EA=B0=81?= =?UTF-8?q?=EB=B0=A5=20=EC=8B=A0=EC=B2=AD=20=EC=B7=A8=EC=86=8C=20=EA=B8=B0?= =?UTF-8?q?=EB=8A=A5=20=EC=B6=94=EA=B0=80=20&=20=ED=8A=B9=EC=A0=95=20?= =?UTF-8?q?=EB=AA=A8=EA=B0=81=EB=B0=A5=20=EC=8B=A0=EC=B2=AD=EB=82=B4?= =?UTF-8?q?=EC=97=AD=20=ED=99=95=EC=9D=B8=20(#43)?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/controllers/participations.controller.ts | 38 ++++++++++- src/services/participations.service.ts | 71 ++++++++++++++++++-- 2 files changed, 102 insertions(+), 7 deletions(-) diff --git a/src/controllers/participations.controller.ts b/src/controllers/participations.controller.ts index 60e2bbf..fb035cf 100644 --- a/src/controllers/participations.controller.ts +++ b/src/controllers/participations.controller.ts @@ -1,4 +1,12 @@ -import { Body, Controller, Post } from "@nestjs/common"; +import { + Body, + Controller, + Delete, + Get, + NotFoundException, + Param, + Post, +} from "@nestjs/common"; import { CurrentMemberDecorator } from "@APP/common/decorators/current-member.decorator"; import { CreateParticipationDto } from "@APP/dtos/create-participation.dto"; @@ -12,6 +20,23 @@ export class ParticipationsController { private readonly articlesService: ArticlesService, ) {} + @Get(":participationId") + async getParticipation( + @Param("participationId") participationId: number, + @CurrentMemberDecorator("id") currentMemberId: number, + ) { + const participation = await this.participationsService.getParticipation( + participationId, + currentMemberId, + ); + + if (!participation) { + throw new NotFoundException("참여 정보를 찾을 수 없습니다."); + } + + return participation; + } + @Post() async postParticipation( @Body() body: CreateParticipationDto, @@ -24,4 +49,15 @@ export class ParticipationsController { body, ); } + + @Delete(":participationId") + async deleteParticipation( + @Param("participationId") participationId: number, + @CurrentMemberDecorator("id") currentMemberId: number, + ) { + return await this.participationsService.deleteParticipation( + participationId, + currentMemberId, + ); + } } diff --git a/src/services/participations.service.ts b/src/services/participations.service.ts index 16f86a1..cf502a7 100644 --- a/src/services/participations.service.ts +++ b/src/services/participations.service.ts @@ -1,5 +1,10 @@ -import { Injectable } from "@nestjs/common"; +import { + ConflictException, + Injectable, + NotFoundException, +} from "@nestjs/common"; +import { ParticipationStatus } from "@APP/common/enum/participation-status.enum"; import { CreateParticipationDto } from "@APP/dtos/create-participation.dto"; import { ParticipationRepository } from "@APP/repositories/participation.repository"; @@ -9,25 +14,79 @@ export class ParticipationsService { private readonly participationsRepository: ParticipationRepository, ) {} + async getParticipation(participationId: number, currentMemberId: number) { + return await this.participationsRepository.findOne({ + where: { id: participationId, memberId: currentMemberId }, + }); + } + async createParticipation( currentMemberId: number, body: CreateParticipationDto, ) { - const newParticipation = this.createParticipationEntity( - currentMemberId, - body, - ); + const participation = await this.participationsRepository.findOne({ + where: { + memberId: currentMemberId, + articleId: body.articleId, + }, + }); + + if (!participation) { + const newParticipation = this.createParticipationEntity( + currentMemberId, + body, + ); + + return await this.participationsRepository.save(newParticipation); + } + + if (participation.status === ParticipationStatus.CANCELLED) { + const updatedParticipation = this.createParticipationEntity( + currentMemberId, + body, + ParticipationStatus.ACTIVE, + ); + + return await this.participationsRepository.save( + updatedParticipation, + ); + } - return await this.participationsRepository.save(newParticipation); + throw new ConflictException("이미 참여한 게시글입니다."); } private createParticipationEntity( currentMemberId: number, body: CreateParticipationDto, + status?: ParticipationStatus, ) { return this.participationsRepository.create({ memberId: currentMemberId, ...body, + status, }); } + + async deleteParticipation( + participationId: number, + currentMemberId: number, + ) { + const participation = await this.participationsRepository.findOne({ + where: { id: participationId, memberId: currentMemberId }, + }); + + if (!participation) { + throw new NotFoundException("참여 정보를 찾을 수 없습니다."); + } + + await this.participationsRepository.update( + { + id: participationId, + memberId: currentMemberId, + }, + { + status: ParticipationStatus.CANCELLED, + }, + ); + } }