Skip to content

fix(api,validators,mobile): Prisma 에러 핸들링 강화 및 Query DTO 타입 안전성 개선 (#118)#119

Merged
dydals3440 merged 6 commits intomainfrom
feature/prisma-error-handling-and-query-dto
Feb 6, 2026
Merged

fix(api,validators,mobile): Prisma 에러 핸들링 강화 및 Query DTO 타입 안전성 개선 (#118)#119
dydals3440 merged 6 commits intomainfrom
feature/prisma-error-handling-and-query-dto

Conversation

@dydals3440
Copy link
Contributor

📋 개요

Prisma unique constraint 위반(P2002) race condition 방어, Query DTO 타입 안전성 강화, TodoCategory 삭제 로직 개선, Mobile 에러 메시지 추가

🏷️ 변경 유형

  • feat - 새로운 기능 추가
  • 🐛 fix - 버그 수정

📦 영향 범위

  • apps/api - NestJS 백엔드
  • apps/mobile - Expo 모바일 앱
  • packages/validators - Zod 스키마

📝 변경 내용

1. GlobalExceptionFilter P2002 매핑 (559885c)

  • Prisma P2002 에러를 constraint별로 구체적인 BusinessException으로 자동 변환
  • 미지의 constraint는 SYS_0004로 폴백 + warn 로그
  • 테스트 6개 추가

2. 서비스별 P2002 race condition 방어 (3e08efe)

  • auth.service: 이메일 중복 가입 → emailAlreadyRegistered
  • oauth.service: 계정 연결 중복 → provider별 alreadyLinked + 헬퍼 메서드 추출
  • follow.service: 중복 친구 요청 → followRequestAlreadySent
  • notification.service: P2025(record not found)만 무시, 나머지 re-throw
  • 테스트 6개 추가

3. TodoCategory P2002 방어 및 삭제 로직 개선 (c37dcd8)

  • create/update에 P2002 → todoCategoryNameDuplicate 매핑
  • 삭제 시 할 일 존재 에러: TODO_CATEGORY_0856TODO_CATEGORY_0855 (todoCategoryHasTodos)
  • moveToCategoryId === categoryId 자기 자신 이동 방지 (SYS_0002)
  • E2E 테스트 추가

4. Cheer/Nudge Query DTO 추가 (4420ca9)

  • @aido/validatorsgetCheersQuerySchema, getNudgesQuerySchema 추가
  • GetCheersQueryDto, GetNudgesQueryDto 생성 (nestjs-zod)
  • 컨트롤러에서 수동 Number() 파싱 제거 → @Query() query: DTO 자동 파싱

5. Mobile 에러 메시지 추가 (f711e7f)

  • USER_0611, TODO_0810, TODO_CATEGORY_0851~0856 한국어 메시지 추가

🧪 테스트

테스트 방법

pnpm test:unit apps/api/src/common/exception/filters/global-exception.filter.spec.ts
pnpm test:unit apps/api/src/modules/auth/services/auth.service.spec.ts
pnpm test:unit apps/api/src/modules/auth/services/oauth.service.spec.ts
pnpm test:unit apps/api/src/modules/follow/follow.service.spec.ts
pnpm test:unit apps/api/src/modules/notification/notification.service.spec.ts
pnpm test:unit apps/api/src/modules/todo-category/todo-category.service.spec.ts

테스트 결과

  • 단위 테스트 통과
  • 통합 테스트 통과
  • 수동 테스트 완료

✅ 체크리스트

작성자 확인

  • 코드가 프로젝트의 코딩 컨벤션을 따릅니다
  • pnpm check (Biome) 검사를 통과했습니다
  • 변경사항에 대한 테스트를 작성/수정했습니다
  • 커밋 메시지가 Conventional Commits 규칙을 따릅니다

🔗 관련 이슈

Closes #118

Prisma unique constraint 위반(P2002)을 자동으로 BusinessException으로
변환하는 로직 추가. 알려진 constraint는 구체적 에러코드로, 미지의
constraint는 SYS_0004로 폴백 처리.
auth, oauth, follow, notification 서비스에서 unique constraint 위반
(P2002) 발생 시 구체적인 BusinessException으로 변환하도록 개선.
동시 요청(race condition) 시에도 적절한 에러 응답을 반환.

- auth.service: 이메일 중복 가입 시 emailAlreadyRegistered
- oauth.service: 계정 연결 중복 시 provider별 alreadyLinked
- follow.service: 중복 친구 요청 시 followRequestAlreadySent
- notification.service: P2025만 무시하고 나머지 에러는 re-throw
- create/update에 P2002 race condition 방어 추가
- 삭제 시 할 일이 있으면 todoCategoryHasTodos(0855) 에러 반환
- moveToCategoryId가 삭제 대상과 같으면 invalidParameter(SYS_0002) 반환
- 컨트롤러 API 문서 에러 테이블 업데이트
컨트롤러에서 수동 string→number 파싱을 제거하고 Zod 스키마 기반
DTO로 교체하여 타입 안전성과 유효성 검증 강화.

- validators: getCheersQuerySchema, getNudgesQuerySchema 추가
- api: GetCheersQueryDto, GetNudgesQueryDto 생성
- controller: @query() DTO 자동 파싱으로 전환
USER_0611, TODO_0810, TODO_CATEGORY_0851~0856 에러코드에 대한
사용자 친화적 한국어 메시지 추가.
@dydals3440 dydals3440 added type: feat 🚀 신규 기능 - 사용자에게 새로운 비즈니스 가치를 제공하는 작업 type: fix 🐛 버그 수정 - 사용자 이탈을 방지하고 시스템 안정성을 확보하는 작업 scope: api 🌐 API - NestJS 서버 로직, DB 스키마 및 백엔드 인프라 관련 scope: mobile 📱 모바일 - Expo 기반 모바일 앱 UI/UX 및 클라이언트 로직 관련 scope: validators 📐 검증 - Zod 스키마 등 서버/앱 간 공유되는 데이터 정합성 관련 status: needs review 🔍 리뷰 대기 - 작업 완료 후 병목 제거를 위해 팀원의 빠른 피드백이 필요한 상태 labels Feb 6, 2026
@dydals3440 dydals3440 self-assigned this Feb 6, 2026
@gemini-code-assist
Copy link

Summary of Changes

Hello @dydals3440, I'm Gemini Code Assist1! I'm currently reviewing this pull request and will post my feedback shortly. In the meantime, here's a summary to help you and other reviewers quickly get up to speed!

이 Pull Request는 백엔드 API의 견고성을 크게 향상시키고, 모바일 앱의 사용자 경험을 개선하는 데 중점을 둡니다. 특히, 데이터베이스의 고유 제약 조건 위반과 관련된 동시성 문제를 효과적으로 처리하기 위한 에러 핸들링 로직을 강화하고, API 쿼리 파라미터의 타입 안전성을 높여 개발 편의성과 안정성을 확보했습니다. 또한, 특정 비즈니스 로직(예: 할 일 카테고리 삭제)의 유효성 검사를 개선하고, 모바일 앱에 더 명확한 에러 메시지를 제공하여 전반적인 시스템의 신뢰도를 높였습니다.

Highlights

  • Prisma P2002 에러 핸들링 강화: Prisma의 고유 제약 조건 위반(P2002) 에러를 GlobalExceptionFilter에서 자동으로 감지하여, 특정 제약 조건(예: 이메일 중복, 카테고리 이름 중복, 팔로우 요청 중복, 계정 연결 중복)에 따라 구체적인 BusinessException으로 매핑하도록 개선되었습니다. 알려지지 않은 제약 조건에 대해서는 SYS_0004로 폴백 처리하며 경고 로그를 남깁니다.
  • 서비스별 P2002 Race Condition 방어 로직 추가: 회원가입(auth.service), OAuth 계정 연결(oauth.service), 친구 요청(follow.service) 등 여러 서비스에서 동시성 문제로 인한 P2002 에러 발생 시, 각 상황에 맞는 BusinessException을 명확하게 반환하도록 로직이 추가되었습니다. notification.service에서는 푸시 토큰 삭제 시 P2025(레코드 없음) 에러는 무시하고, 다른 Prisma 에러는 다시 던지도록 처리했습니다.
  • TodoCategory 삭제 로직 개선 및 에러 코드 변경: TodoCategory 삭제 시, 해당 카테고리에 할 일이 남아있는데 이동할 카테고리를 지정하지 않으면 TODO_CATEGORY_0855 에러를 반환하도록 변경되었습니다. 또한, 삭제하려는 카테고리와 이동 대상 카테고리가 동일할 경우 SYS_0002 에러를 발생시켜 잘못된 요청을 방지합니다.
  • Query DTO 타입 안전성 개선 (Cheer/Nudge): @aido/validators 패키지에 getCheersQuerySchemagetNudgesQuerySchema Zod 스키마가 추가되었고, 이를 기반으로 GetCheersQueryDtoGetNudgesQueryDto가 생성되었습니다. 이로써 컨트롤러에서 쿼리 파라미터의 수동 Number() 파싱이 제거되고, NestJS-Zod를 통한 자동 파싱으로 타입 안전성이 강화되었습니다.
  • 모바일 앱 에러 메시지 현지화 추가: 모바일 앱에서 사용자에게 표시될 USER_0611, TODO_0810, TODO_CATEGORY_0851부터 TODO_CATEGORY_0856까지의 에러 코드에 대한 한국어 메시지가 추가되어 사용자 경험이 개선되었습니다.
Changelog
  • apps/api/src/common/exception/filters/global-exception.filter.spec.ts
    • Prisma P2002 에러 매핑 테스트 케이스 추가 (email, userId_name, followerId_followingId)
    • 알 수 없는 P2002 제약 조건에 대한 SYS_0004 폴백 테스트 추가
    • P2002가 아닌 Prisma 에러에 대한 SYS_0001 처리 테스트 추가
  • apps/api/src/common/exception/filters/global-exception.filter.ts
    • PrismaClientKnownRequestError (P2002) 처리를 위한 mapP2002ToBusinessException 메서드 추가
    • P2002 에러를 특정 BusinessException으로 매핑하는 로직 구현 (이메일, 사용자 태그, 카테고리 이름, 팔로우, 계정 연결)
    • 알 수 없는 P2002 제약 조건에 대한 SYS_0004 (concurrentModification) 폴백 처리 및 경고 로깅 추가
  • apps/api/src/modules/auth/services/auth.service.spec.ts
    • 회원가입 시 P2002 (이메일 중복) 에러 발생 시 emailAlreadyRegistered를 던지는 테스트 추가
  • apps/api/src/modules/auth/services/auth.service.ts
    • 사용자 등록 트랜잭션 내에서 P2002 에러 발생 시 emailAlreadyRegistered 예외를 처리하도록 변경
  • apps/api/src/modules/auth/services/oauth.service.spec.ts
    • 계정 연결 시 P2002 (provider별 alreadyLinked) 에러 발생 시 해당 BusinessException을 던지는 테스트 추가
  • apps/api/src/modules/auth/services/oauth.service.ts
    • 계정 연결 시 P2002 에러를 처리하여 provideralreadyLinked 예외를 던지도록 로직 추가
    • 제공자별 계정 연결 중복 예외를 반환하는 헬퍼 메서드 getAlreadyLinkedExceptionForProvider 추가
  • apps/api/src/modules/cheer/cheer.controller.ts
    • getReceivedCheersgetSentCheers 엔드포인트에서 쿼리 파라미터 파싱을 GetCheersQueryDto를 사용하도록 변경
    • 수동 Number() 파싱 로직 제거
  • apps/api/src/modules/cheer/dtos/request/get-cheers-query.dto.ts
    • 응원 목록 조회 쿼리 파라미터의 타입 안전성을 위한 GetCheersQueryDto 파일 추가
  • apps/api/src/modules/cheer/dtos/request/index.ts
    • get-cheers-query.dto 내보내기 추가
  • apps/api/src/modules/follow/follow.service.spec.ts
    • 친구 요청 시 P2002 (중복 요청) 에러 발생 시 followRequestAlreadySent를 던지는 테스트 추가
  • apps/api/src/modules/follow/follow.service.ts
    • 친구 요청(sendRequest) 및 자동 수락 로직에서 P2002 에러 발생 시 followRequestAlreadySent 예외를 처리하도록 변경
  • apps/api/src/modules/notification/notification.service.spec.ts
    • 푸시 토큰 삭제 시 P2025 에러(레코드 없음)는 무시하고 정상 반환하는 테스트 추가
    • P2025가 아닌 다른 Prisma 에러 및 일반 에러는 re-throw하는 테스트 추가
  • apps/api/src/modules/notification/notification.service.ts
    • unregisterPushToken 메서드에서 Prisma P2025 에러(레코드 없음)는 무시하고 경고 로그를 남기도록 변경
    • P2025 외의 다른 에러는 다시 던지도록 처리
  • apps/api/src/modules/nudge/dtos/request/get-nudges-query.dto.ts
    • 콕 찌름 목록 조회 쿼리 파라미터의 타입 안전성을 위한 GetNudgesQueryDto 파일 추가
  • apps/api/src/modules/nudge/dtos/request/index.ts
    • get-nudges-query.dto 내보내기 추가
  • apps/api/src/modules/nudge/nudge.controller.ts
    • getReceivedNudgesgetSentNudges 엔드포인트에서 쿼리 파라미터 파싱을 GetNudgesQueryDto를 사용하도록 변경
    • 수동 Number() 파싱 로직 제거
  • apps/api/src/modules/todo-category/todo-category.controller.ts
    • DELETE /todo-categories/{id} API 문서 업데이트: TODO_CATEGORY_0856TODO_CATEGORY_0855로 변경, SYS_0002 에러 케이스 추가
  • apps/api/src/modules/todo-category/todo-category.service.spec.ts
    • 카테고리 생성/수정 시 P2002 (이름 중복) 에러 발생 시 todoCategoryNameDuplicate를 던지는 테스트 추가
    • 카테고리 삭제 시 할 일이 있는데 moveToCategoryId가 없는 경우 TODO_CATEGORY_0855를 던지는 테스트 업데이트
    • moveToCategoryId가 삭제 대상과 같을 경우 invalidParameter (SYS_0002)를 던지는 테스트 추가
  • apps/api/src/modules/todo-category/todo-category.service.ts
    • 카테고리 생성/수정 시 P2002 에러 발생 시 todoCategoryNameDuplicate 예외를 처리하도록 변경
    • 카테고리 삭제 로직 개선: 할 일이 있는 카테고리 삭제 시 moveToCategoryId가 없으면 todoCategoryHasTodos (0855) 예외 발생
    • 카테고리 삭제 로직 개선: moveToCategoryId가 삭제 대상 카테고리와 같으면 invalidParameter (SYS_0002) 예외 발생
  • apps/api/test/e2e/todo-category.e2e-spec.ts
    • E2E 테스트에서 카테고리 삭제 시 할 일이 있는 경우 TODO_CATEGORY_0856 대신 TODO_CATEGORY_0855 에러 코드를 확인하도록 업데이트
    • E2E 테스트에서 moveToCategoryId가 삭제 대상과 같을 경우 SYS_0002 에러 코드를 확인하는 테스트 추가
  • apps/mobile/src/shared/infra/http/error-handler.ts
    • USER_0611: '계정 설정에 문제가 있어요. 다시 시도해주세요.' 메시지 추가
    • TODO_0810: '이동할 위치의 할 일을 찾을 수 없어요' 메시지 추가
    • TODO_CATEGORY_0851~TODO_CATEGORY_0856에 대한 한국어 에러 메시지 추가
  • packages/validators/src/domains/cheer/cheer.request.ts
    • 응원 목록 조회 쿼리 파라미터 유효성 검사를 위한 getCheersQuerySchema (Zod) 추가
    • GetCheersQuery 타입 정의
  • packages/validators/src/domains/nudge/nudge.request.ts
    • 콕 찌름 목록 조회 쿼리 파라미터 유효성 검사를 위한 getNudgesQuerySchema (Zod) 추가
    • GetNudgesQuery 타입 정의
Activity
  • dydals3440 님이 PR을 생성하고 초기 변경 사항을 제출했습니다.
  • dydals3440 님이 Prisma P2002 에러 핸들링, 서비스별 Race Condition 방어, TodoCategory 로직 개선, Query DTO 타입 안전성 강화, 모바일 에러 메시지 추가 등 여러 커밋을 통해 기능을 구현하고 테스트를 추가했습니다.
Using Gemini Code Assist

The full guide for Gemini Code Assist can be found on our documentation page, here are some quick tips.

Invoking Gemini

You can request assistance from Gemini at any point by creating a comment using either /gemini <command> or @gemini-code-assist <command>. Below is a summary of the supported commands on the current page.

Feature Command Description
Code Review /gemini review Performs a code review for the current pull request in its current state.
Pull Request Summary /gemini summary Provides a summary of the current pull request in its current state.
Comment @gemini-code-assist Responds in comments when explicitly tagged, both in pull request comments and review comments.
Help /gemini help Displays a list of available commands.

Customization

To customize Gemini Code Assist for GitHub experience, repository maintainers can create a configuration file and/or provide a custom code review style guide (such as PEP-8 for Python) by creating and adding files to a .gemini/ folder in the base of the repository. Detailed instructions can be found here.

Limitations & Feedback

Gemini Code Assist may make mistakes. Please leave feedback on any instances where its feedback is incorrect or counter productive. You can react with 👍 and 👎 on @gemini-code-assist comments. If you're interested in giving your feedback about your experience with Gemini Code Assist for Github and other Google products, sign up here.

You can also get AI-powered code generation, chat, as well as code reviews directly in the IDE at no cost with the Gemini Code Assist IDE Extension.

Footnotes

  1. Review the Privacy Notices, Generative AI Prohibited Use Policy, Terms of Service, and learn how to configure Gemini Code Assist in GitHub here. Gemini can make mistakes, so double check it and use code with caution.

@dydals3440 dydals3440 requested a review from hijjoy February 6, 2026 07:10
Copy link

@gemini-code-assist gemini-code-assist bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Code Review

전반적으로 훌륭한 PR입니다. Prisma P2002 에러에 대한 서비스 레벨 및 글로벌 핸들링을 추가하여 동시성 문제에 대한 방어 코드를 강화한 점이 인상적입니다. 특히 GlobalExceptionFilter를 통해 알려지지 않은 제약 조건에 대한 폴백 처리를 구현한 것은 시스템 안정성을 크게 높일 것입니다. GetCheersQueryDtoGetNudgesQueryDto를 도입하여 수동 파싱 로직을 제거하고 타입 안전성을 개선한 부분도 좋은 리팩터링입니다.

AuthService의 에러 핸들링을 더 명확하게 하여 잠재적인 버그를 방지하는 내용의 추가 개선 제안을 리뷰 코멘트로 남겼습니다. 코드 병합 전에 확인해주시면 좋겠습니다.

P2002 catch 블록이 모든 unique constraint 위반을 이메일 중복으로
간주하던 문제 수정. error.meta.target에 email이 포함된 경우만
emailAlreadyRegistered를 던지고, 나머지는 GlobalExceptionFilter로
위임하도록 re-throw 처리.
@dydals3440 dydals3440 merged commit 321eff2 into main Feb 6, 2026
3 checks passed
@dydals3440 dydals3440 deleted the feature/prisma-error-handling-and-query-dto branch February 6, 2026 07:33
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

scope: api 🌐 API - NestJS 서버 로직, DB 스키마 및 백엔드 인프라 관련 scope: mobile 📱 모바일 - Expo 기반 모바일 앱 UI/UX 및 클라이언트 로직 관련 scope: validators 📐 검증 - Zod 스키마 등 서버/앱 간 공유되는 데이터 정합성 관련 status: needs review 🔍 리뷰 대기 - 작업 완료 후 병목 제거를 위해 팀원의 빠른 피드백이 필요한 상태 type: feat 🚀 신규 기능 - 사용자에게 새로운 비즈니스 가치를 제공하는 작업 type: fix 🐛 버그 수정 - 사용자 이탈을 방지하고 시스템 안정성을 확보하는 작업

Projects

None yet

Development

Successfully merging this pull request may close these issues.

[Feature]: Prisma 에러 핸들링 강화 및 Query DTO 타입 안전성 개선

1 participant