[TIL] Work-Flow 프로젝트 - Membership, payment (1/4) 23.08.25

이상훈·2023년 8월 28일
0

[내일배움캠프]

목록 보기
59/68
  • 프리미엄 멤버십과 무료 두 가지로 서비스를 운용하기로 함
  • 무료버전의 경우 보드는 3개까지만 생성가능, 멤버는 5명까지만 초대가능
  // 멤버십 결제
  async purchaseMembership(body: MembershipDto, workspaceId: number, userId: number): Promise<IResult> {
    const entityManager = this.paymentRepository.manager;

    await entityManager.transaction(async (transactionEntityManager: EntityManager) => {
      const findUserById = await this.userService.findUserById(userId);

      if (findUserById.points < body.packagePrice)
        throw new HttpException('포인트가 부족합니다', HttpStatus.BAD_REQUEST);
      findUserById.points -= body.packagePrice;
      await transactionEntityManager.save(findUserById);

      const newPayment = this.paymentRepository.create({
        workspaceId,
        user: { id: userId },
      });
      await transactionEntityManager.save(newPayment);
      await this.membershipService.createMembership(body, workspaceId);
    });

    return { result: true };
  }

entityManager를 사용하여 트랜잭션을 걸어줌. 우선 현재 접속중인 유저의 포인트를 조회한 뒤 결제에 문제가 없다면 새로운 payment를 생성해주고 멤버십을 생성

  // 멤버십 생성
  async createMembership(body: MembershipDto, workspaceId: number): Promise<IResult> {
    const startDate = new Date();
    const servicePeriod = body.servicePeriod * 24 * 60 * 60 * 1000;
    const endDate = new Date(startDate.getTime() + servicePeriod);

    const existMembership = await this.membershipRepository.findOne({ where: { workspace: { id: workspaceId } } });
    if (existMembership) throw new HttpException('이미 멤버십 결제가 되어있습니다.', HttpStatus.CONFLICT);

    const newMembership = this.membershipRepository.create({
      package_type: body.packageType,
      package_price: body.packagePrice,
      end_date: endDate,
      workspace: { id: workspaceId },
    });

    await this.membershipRepository.save(newMembership);

    return { result: true };
  }

이용기간은 body값으로 30일 또는 180일만 들어오게 되어있고 시작일에 해당 body값의 기간을 더해주어 끝나는 날짜를 계산 후 생성

멤버십은 워크스페이스 단위로 적용되기 때문에 결제의 경우 member role이 Admin일 경우에만 가능하게 구현

 // 결제
  @Post()
  @UseGuards(AuthGuard)
  @UseInterceptors(CheckAdminInterceptor)
  async purchaseMembership(
    @Body() body: MembershipDto,
    @Param('workspaceId') workspaceId: number,
    @GetUser() user: AccessPayload
  ): Promise<IResult> {
    return await this.paymentService.purchaseMembership(body, workspaceId, user.id);
  }

membe role이 Admin인지 체크하는 interceptor를 만들어서 해당 api가 실행될 때 검사

profile
코린이

0개의 댓글