Skip to content

feat: 판결 결과 페이지 구현 (판결/유형 탭, JudgmentResult, JudgmentTypeResult) - #90

Merged
evenif99 merged 10 commits into
devfrom
feature/judgement-result
Jun 20, 2026
Merged

feat: 판결 결과 페이지 구현 (판결/유형 탭, JudgmentResult, JudgmentTypeResult)#90
evenif99 merged 10 commits into
devfrom
feature/judgement-result

Conversation

@wjdalss21

@wjdalss21 wjdalss21 commented Jun 20, 2026

Copy link
Copy Markdown
Collaborator

Summary

  • 판결 결과 페이지 구현: 판결/유형 서브탭, JudgmentResult, JudgmentTypeResult 컴포넌트 추가
  • DisputePage에 서브탭 렌더링 연결 및 판결 완료/종료 상태 노출
  • 유형 결과 카드 이미지 Supabase Storage URL 지원 (next.config.ts remotePatterns 추가)
  • ActionPrompt 공통 컴포넌트 활용 (공유/다운로드 버튼)
  • 카드 이미지 원본 비율 유지 (width={0} height={0} sizes="100vw")

Review Fixes

  • nickname → name: DisputeParticipantDto, route, 컴포넌트, useActiveCases 전체 반영
  • next.config.ts: 카카오 HTTP 패턴 제거 (HTTPS만 허용)
  • DisputePage: isCompleted에서 null 케이스 처리 (!!dispute)
  • SCSS stylelint: @include 뒤 빈 줄 추가 (declaration-empty-line-before)
  • JudgmentResult / JudgmentTypeResult: props 대신 disputeId 기반 직접 API 호출 (새로고침 시 데이터 유실 방지, TanStack Query 캐시로 중복 요청 없음)
  • lib/auth/index.ts: 프로필 이미지 백필 실패 시 로그인 차단 방지 (try-catch 감싸기)
  • judgement.api.ts: 에러 메시지 사용자 친화적으로 개선
  • 머지 충돌 해결: lib/auth/index.ts (profileImageUrl + deletedAt 모두 select)

Test Plan

  • 판결 완료 사건 진입 → 판결/유형 서브탭 노출 확인
  • 판결 탭: A/B 잘못, 화해 제안 카드 정상 렌더링 확인
  • 유형 탭: Supabase 카드 이미지 정상 로딩 및 원본 비율 유지 확인
  • 유형 탭: 이미지 없을 때 유형명 fallback 노출 확인
  • 새로고침 후 판결/유형 탭 데이터 정상 유지 확인
  • 참여자 이름(name) 판결 카드에 정상 노출 확인
  • 단독/2인 판결 모두 동작 확인

🤖 Generated with Claude Code

Summary by CodeRabbit

릴리스 노트

  • New Features

    • 판결 완료 시 판결/유형 결과를 서브탭으로 구분해 표시
    • 판결 결과 카드 UI(이미지/아바타 포함)와 로딩/실패/빈 상태에 대한 안내 제공
    • 참여자 정보에 프로필 이미지와 이름이 반영(케이스 및 상세/결과 화면)
  • Bug Fixes

    • 사건 상태 배지의 “초안” 라벨을 “작성중”으로 수정

wjdalss21 and others added 6 commits June 20, 2026 11:30
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
- DisputePage: 판결/유형 서브탭(Tab 공통컴포넌트) 추가
- JudgmentResult: 이미지 기준 UI 재구성, nickname 적용
- JudgmentTypeResult: 유형탭 컴포넌트 신규 생성 (카드이미지, ActionPrompt)
- Tab.module.scss: w60 h36 사이즈 조정
- DisputeParticipantDto: nickname 필드 추가
- disputes/[id]/route: nickname 조회 추가
- judgment.mapper: cardImageUrl 추가
- types/judgment: ConflictTypeDetailDto에 cardImageUrl 추가
- auth/index: 카카오 로그인 시 profileImageUrl 저장
- page.module.scss: diaryBox max-width 제거
- NewCaseButton: AbortController timeout 30s

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
@vercel

vercel Bot commented Jun 20, 2026

Copy link
Copy Markdown

The latest updates on your projects. Learn more about Vercel for GitHub.

Project Deployment Actions Updated (UTC)
talky-owl Ready Ready Preview, Comment Jun 20, 2026 7:10am

@coderabbitai

coderabbitai Bot commented Jun 20, 2026

Copy link
Copy Markdown
Contributor

Review Change Stack

No actionable comments were generated in the recent review. 🎉

ℹ️ Recent review info
⚙️ Run configuration

Configuration used: Repository UI (base), Organization UI (inherited)

Review profile: CHILL

Plan: Pro Plus

Run ID: b3e54704-af9e-4266-9b2d-5b502767fec0

📥 Commits

Reviewing files that changed from the base of the PR and between 4f42530 and 82daceb.

📒 Files selected for processing (5)
  • src/app/(page)/disputes/[id]/page.tsx
  • src/components/judgement/JudgmentResult.tsx
  • src/components/judgement/JudgmentTypeResult.tsx
  • src/domains/judgement/judgement.api.ts
  • src/lib/auth/index.ts
🚧 Files skipped from review as they are similar to previous changes (3)
  • src/app/(page)/disputes/[id]/page.tsx
  • src/domains/judgement/judgement.api.ts
  • src/lib/auth/index.ts

📝 Walkthrough

Walkthrough

분쟁 상세 페이지에서 판결 완료/종료 상태에만 판결 결과 데이터를 로딩하고, 판결/유형 서브탭을 통해 렌더링합니다. 참여자의 실명과 프로필 이미지 URL이 API 응답에 포함되며, 카카오 로그인 시 프로필 이미지가 저장됩니다.

Changes

판결 결과 렌더링 및 연관 인프라

Layer / File(s) Summary
판결 DTO 타입 및 매퍼 확장
src/types/judgment.ts, src/domains/judgement/judgment.mapper.ts
ConflictTypeDetailDtocardImageUrl: string | null 필드를 추가하고, toAiJudgmentDto 매퍼에서 원본의 card_image_url을 해당 필드로 매핑한다.
참여자 실명 API 전달 경로
src/app/api/disputes/[id]/route.ts, src/app/api/disputes/route.ts, src/types/dispute.ts, src/hooks/useActiveCases.ts
분쟁 상세/목록 조회 API의 Prisma 쿼리에서 participants.user.name을 select하고, toParticipantDto가 실제 사용자 이름을 반환하도록 변경한다. DisputeParticipantDto 타입도 nickname 대신 name으로 정의하며, 활성 사건 목록도 동일하게 업데이트된다.
판결 조회 API 함수 및 React Query 훅
src/domains/judgement/judgement.api.ts, src/domains/judgement/judgement.hooks.ts
parseJson 헬퍼와 fetchJudgment 함수로 /api/disputes/${disputeId}/result 엔드포인트를 호출하고, useJudgment 훅이 isCompleted 조건 하에서만 쿼리를 실행한다.
JudgmentResult 판결 결과 컴포넌트
src/components/judgement/JudgmentResult.tsx, src/components/judgement/JudgmentResult.module.scss
참여자 수(1인/2인)에 따라 잘못 카드와 화해 제안 섹션을 조건부 렌더링한다. 각 카드의 프로필 이미지 또는 fallback, 그리고 사용자 이름 또는 기본 라벨(A/B)을 표시한다.
JudgmentTypeResult 유형 결과 컴포넌트
src/components/judgement/JudgmentTypeResult.tsx, src/components/judgement/JudgmentTypeResult.module.scss
역할_a 참여자의 이름을 제목에 표시하고, 카드 이미지 또는 텍스트 fallback으로 유형을 렌더링한다. 공유/다운로드 버튼은 준비 중 토스트를 표시한다.
DisputePage 판결 탭 서브탭 통합
src/app/(page)/disputes/[id]/page.tsx, src/app/(page)/disputes/[id]/DisputePage.module.scss, src/components/ui/Tab.module.scss
분쟁 상태에 따라 useJudgment 훅을 호출하고, 판결 탭 내부에 판결/유형 서브탭을 추가해 로딩·결과·빈 상태를 조건 분기 렌더링한다. 탭 아이템 스타일을 고정 너비/높이로 변경한다.
카카오 로그인 프로필 이미지 저장
src/lib/auth/index.ts
saveFirstLoginFieldsimageUrl 파라미터를 받아 최초 저장과 닉네임 재시도 시 profileImageUrl을 설정한다. 최초 로그인과 기존 유저의 이미지 누락 시 카카오 이미지로 채운다.
원격 이미지 도메인 허용 및 소규모 변경
next.config.ts, src/components/ui/StatusBadge.tsx, src/components/home/NewCaseButton.tsx
Next.js remotePatterns에 Supabase·Kakao CDN 도메인을 추가하고, StatusBadgedraft 라벨을 변경하며, 불필요한 주석을 정리한다.

Sequence Diagram(s)

sequenceDiagram
  participant User as 사용자
  participant DisputePage as DisputePage
  participant useJudgment as useJudgment 훅
  participant ResultAPI as /api/disputes/[id]/result
  participant JudgmentResult as JudgmentResult
  participant JudgmentTypeResult as JudgmentTypeResult

  User->>DisputePage: 판결 탭 클릭 (judged/closed 상태)
  DisputePage->>useJudgment: useJudgment(id, isCompleted=true)
  useJudgment->>ResultAPI: GET /api/disputes/${id}/result
  ResultAPI-->>useJudgment: AiJudgmentDto
  useJudgment-->>DisputePage: judgment, judgmentLoading
  
  alt judgmentLoading
    DisputePage-->>User: 로딩 스피너 표시
  else judgment 존재
    DisputePage->>DisputePage: 판결/유형 서브탭 렌더링
    alt 판결 서브탭
      DisputePage->>JudgmentResult: judgment, participants 전달
      JudgmentResult-->>User: 잘못 카드 + 화해 제안 표시
    else 유형 서브탭
      DisputePage->>JudgmentTypeResult: judgment, participants 전달
      JudgmentTypeResult-->>User: 유형 카드 이미지 + 액션 표시
    end
  else judgment 없음
    DisputePage-->>User: 빈 결과 메시지
  end
Loading

Estimated code review effort

🎯 4 (Complex) | ⏱️ ~60 minutes

Possibly related PRs

  • I5-Project/TALKY-OWL#53: 분쟁 상세 페이지(disputes/[id]/page.tsx)의 판결 탭 흐름을 useJudgment 기반 실제 렌더링으로 확장한 선행 변경사항.
  • I5-Project/TALKY-OWL#83: toParticipantDto 매핑 로직과 DisputeParticipantDto 필드 변경을 동일 코드 경로에서 수정하는 연관 작업.
  • I5-Project/TALKY-OWL#70: Prisma 스키마와 AI 판결 생성 API(/api/disputes/[id]/judge)에서 역할별 판결 JSON 필드를 구현하는 백엔드 기반 작업.

Poem

🦉 토끼가 판결을 내리네,
잘못 카드, 유형 카드 사르르~
닉네임도 프로필도 쏙쏙 담고,
카카오 이미지도 빠짐없이!
🐇 재판 결과, 이제 화면에 피어나요 🌸

🚥 Pre-merge checks | ✅ 3 | ❌ 2

❌ Failed checks (1 warning, 1 inconclusive)

Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 26.67% which is insufficient. The required threshold is 80.00%. Write docstrings for the functions missing them to satisfy the coverage threshold.
Description check ❓ Inconclusive PR 설명에서 필수 항목 대부분(Summary, Review Fixes, Test Plan)이 포함되어 있으나, 저장소의 공식 템플릿 섹션(작업 내용, 담당 영역, Issue, 테스트 결과 체크박스 등)이 채워지지 않았습니다. 저장소 공식 템플릿의 필수 섹션(1-12번)을 완성하거나, 현재 작성된 Summary 형식이 승인된 대체 형식인지 확인이 필요합니다.
✅ Passed checks (3 passed)
Check name Status Explanation
Title check ✅ Passed 제목은 판결 결과 페이지 구현의 주요 변경사항(판결/유형 탭, JudgmentResult, JudgmentTypeResult)을 명확하고 구체적으로 요약하고 있습니다.
Linked Issues check ✅ Passed Check skipped because no linked issues were found for this pull request.
Out of Scope Changes check ✅ Passed Check skipped because no linked issues were found for this pull request.

✏️ Tip: You can configure your own custom pre-merge checks in the settings.

✨ Finishing Touches
📝 Generate docstrings
  • Create stacked PR
  • Commit on current branch
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch feature/judgement-result

Comment @coderabbitai help to get the list of available commands and usage tips.

Comment thread src/app/api/disputes/[id]/route.ts Outdated
type DisputeForDetail = Prisma.DisputeGetPayload<{
include: {
participants: { include: { user: { select: { profileImageUrl: true } } } }
participants: { include: { user: { select: { nickname: true; profileImageUrl: true } } } }

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

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

nickname 쓰나요? name 안쓰고?!

Copy link
Copy Markdown
Collaborator Author

Choose a reason for hiding this comment

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

아 네임이에요?? 저 닉네임인줄 알았습니다 수정하도록 하겠습니다 ㅎㅎ

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

Actionable comments posted: 5

🧹 Nitpick comments (3)
src/components/judgement/JudgmentTypeResult.tsx (1)

23-29: 💤 Low value

공유/다운로드 기능이 placeholder로 구현되어 있습니다.

현재 두 핸들러 모두 "준비 중" 토스트만 표시합니다. 향후 실제 구현이 필요하며, 이슈 트래커에 등록되어 있는지 확인하세요.

실제 기능 구현을 위한 이슈를 생성하거나 구현 가이드가 필요하시면 도와드릴 수 있습니다.

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@src/components/judgement/JudgmentTypeResult.tsx` around lines 23 - 29, The
handleShare and handleDownload functions in JudgmentTypeResult.tsx are currently
placeholder implementations that only show toast messages. Replace these
placeholder implementations with actual share and download functionality. Verify
whether tracking issues or tickets exist for these features, and implement the
real share and download capabilities based on the project requirements. If
implementation details are unclear, consult with the team on the expected
behavior before implementing.
src/components/judgement/JudgmentResult.tsx (1)

13-22: ⚡ Quick win

고정 크기 아바타에는 명시적 width/height 사용을 권장합니다.

현재 width={0} height={0} sizes="100vw" 패턴은 반응형 이미지에 적합하지만, 아바타는 CSS에서 24x24 고정 크기로 렌더링됩니다. Next.js Image 컴포넌트에 명시적 치수를 지정하면 레이아웃 시프트를 방지하고 최적화된 이미지 크기를 선택할 수 있습니다.

♻️ 제안하는 수정
 function Avatar({ src }: { src: string | null }) {
   return (
     <div className={styles.avatar}>
       {src
-        ? <Image src={src} alt="" width={0} height={0} sizes="100vw" className={styles.avatarImg} />
+        ? <Image src={src} alt="" width={24} height={24} className={styles.avatarImg} />
         : <div className={styles.avatarFallback} />
       }
     </div>
   )
 }
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@src/components/judgement/JudgmentResult.tsx` around lines 13 - 22, The Avatar
component in JudgmentResult.tsx uses width={0} height={0} sizes="100vw" pattern
which is designed for responsive images, but since the avatar is rendered at a
fixed 24x24 size in CSS, explicit width and height values should be specified
instead. Update the Image component by replacing width={0} height={0}
sizes="100vw" with explicit width={24} height={24}, and remove the sizes prop,
which is only needed for responsive images. This will prevent layout shifts and
allow Next.js to optimize the image properly for the fixed avatar dimensions.
src/domains/judgement/judgement.api.ts (1)

4-11: ⚖️ Poor tradeoff

타입 안정성 개선을 고려해보세요.

JSON.parse(text) as ApiResponse<T> 캐스팅은 런타임에 서버가 예상과 다른 구조를 반환할 경우 타입 불일치 문제를 발생시킬 수 있습니다. Zod와 같은 런타임 검증 라이브러리를 사용하면 더 안전하게 처리할 수 있습니다.

현재 구현도 일반적인 패턴이며 동작은 하지만, 향후 개선 시 고려해보시기 바랍니다.

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@src/domains/judgement/judgement.api.ts` around lines 4 - 11, The parseJson
function uses an unsafe type cast `as ApiResponse<T>` on the parsed JSON data,
which does not validate that the runtime structure actually matches the expected
ApiResponse<T> type. Instead of relying on a type assertion, implement runtime
validation using a library like Zod to create a schema that validates the JSON
response structure before casting. This ensures that if the server returns data
in an unexpected format, you will catch the validation error rather than
silently accepting mistyped data.
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In `@next.config.ts`:
- Around line 20-22: The current configuration allows HTTP protocol for the
hostname k.kakaocdn.net in the Next.js image configuration, but Kakao's official
API documentation only supports HTTPS for profile image URLs. Remove the HTTP
protocol entry for k.kakaocdn.net in the next.config.ts file, as HTTP endpoints
are not officially supported by Kakao and should not be used.

In `@src/app/`(page)/disputes/[id]/page.tsx:
- Around line 41-43: The isCompleted variable calculation checks for undefined
but not null, which can cause a runtime crash when dispute is null and
dispute.status is accessed. Replace the condition checking dispute !== undefined
with a proper null-safety check that handles both null and undefined cases, such
as using dispute != null or dispute && before accessing dispute.status in the
boolean expression.

In `@src/components/judgement/JudgmentResult.module.scss`:
- Line 88: The stylelint rule `declaration-empty-line-before` requires blank
lines before CSS declarations in certain contexts. Add a blank line before each
of the three color declarations (at the original lines 88, 93, and 100 in the
JudgmentResult.module.scss file) to comply with this formatting rule. Place an
empty line directly before each `color: v.$color-black-400;` statement and any
other declarations that need this spacing.

In `@src/components/judgement/JudgmentTypeResult.module.scss`:
- Line 14: The stylelint rule `declaration-empty-line-before` requires a blank
line to precede property declarations within CSS blocks. Add an empty line
before the `color: v.$color-black-700;` declaration to comply with this
formatting rule. The same issue also appears at another location in the file
(line 42), so apply the same fix there as well by adding a blank line before
that declaration.

In `@src/lib/auth/index.ts`:
- Around line 132-138: The prisma.user.update call within the profileImageUrl
backfill logic (checking !existing.profileImageUrl && user.image) is not wrapped
in error handling. If the database update fails, the exception will propagate
and block the entire authentication flow. Wrap the prisma.user.update operation
in a try-catch block to gracefully handle any database errors, log the error if
needed, but allow the authentication to continue and return true since profile
image backfill is not a critical operation for login success.

---

Nitpick comments:
In `@src/components/judgement/JudgmentResult.tsx`:
- Around line 13-22: The Avatar component in JudgmentResult.tsx uses width={0}
height={0} sizes="100vw" pattern which is designed for responsive images, but
since the avatar is rendered at a fixed 24x24 size in CSS, explicit width and
height values should be specified instead. Update the Image component by
replacing width={0} height={0} sizes="100vw" with explicit width={24}
height={24}, and remove the sizes prop, which is only needed for responsive
images. This will prevent layout shifts and allow Next.js to optimize the image
properly for the fixed avatar dimensions.

In `@src/components/judgement/JudgmentTypeResult.tsx`:
- Around line 23-29: The handleShare and handleDownload functions in
JudgmentTypeResult.tsx are currently placeholder implementations that only show
toast messages. Replace these placeholder implementations with actual share and
download functionality. Verify whether tracking issues or tickets exist for
these features, and implement the real share and download capabilities based on
the project requirements. If implementation details are unclear, consult with
the team on the expected behavior before implementing.

In `@src/domains/judgement/judgement.api.ts`:
- Around line 4-11: The parseJson function uses an unsafe type cast `as
ApiResponse<T>` on the parsed JSON data, which does not validate that the
runtime structure actually matches the expected ApiResponse<T> type. Instead of
relying on a type assertion, implement runtime validation using a library like
Zod to create a schema that validates the JSON response structure before
casting. This ensures that if the server returns data in an unexpected format,
you will catch the validation error rather than silently accepting mistyped
data.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Repository UI (base), Organization UI (inherited)

Review profile: CHILL

Plan: Pro Plus

Run ID: 91a024ee-0fa0-4c51-b20e-d40881e949ee

📥 Commits

Reviewing files that changed from the base of the PR and between 094b3e2 and d6413b9.

⛔ Files ignored due to path filters (3)
  • docs/screenshots/common-components-test.png is excluded by !**/*.png
  • 판결 결과(1인).png is excluded by !**/*.png
  • 판결 결과(2인).png is excluded by !**/*.png
📒 Files selected for processing (18)
  • next.config.ts
  • src/app/(page)/disputes/[id]/DisputePage.module.scss
  • src/app/(page)/disputes/[id]/page.tsx
  • src/app/api/disputes/[id]/route.ts
  • src/app/api/disputes/route.ts
  • src/app/api/personal-analyses/.gitkeep
  • src/components/home/NewCaseButton.tsx
  • src/components/judgement/JudgmentResult.module.scss
  • src/components/judgement/JudgmentResult.tsx
  • src/components/judgement/JudgmentTypeResult.module.scss
  • src/components/judgement/JudgmentTypeResult.tsx
  • src/components/ui/StatusBadge.tsx
  • src/components/ui/Tab.module.scss
  • src/domains/judgement/judgement.api.ts
  • src/domains/judgement/judgement.hooks.ts
  • src/domains/judgement/judgment.mapper.ts
  • src/lib/auth/index.ts
  • src/types/judgment.ts
💤 Files with no reviewable changes (2)
  • src/app/api/disputes/route.ts
  • src/components/home/NewCaseButton.tsx

Comment thread next.config.ts Outdated
Comment thread src/app/(page)/disputes/[id]/page.tsx Outdated
Comment thread src/components/judgement/JudgmentResult.module.scss

.title {
@include m.text-title-s;
color: v.$color-black-700;

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

⚠️ Potential issue | 🟡 Minor | ⚡ Quick win

Stylelint 포맷팅 규칙을 준수하세요.

선언문 앞에 빈 줄을 추가하여 declaration-empty-line-before 규칙을 만족시키세요.

🎨 제안하는 수정
 .title {
   `@include` m.text-title-s;
+
   color: v.$color-black-700;
 }

 .fallbackText {
   `@include` m.text-title-m;
+
   color: v.$color-black-400;
 }

Also applies to: 42-42

🧰 Tools
🪛 Stylelint (17.13.0)

[error] 14-14: Expected empty line before declaration (declaration-empty-line-before)

(declaration-empty-line-before)

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@src/components/judgement/JudgmentTypeResult.module.scss` at line 14, The
stylelint rule `declaration-empty-line-before` requires a blank line to precede
property declarations within CSS blocks. Add an empty line before the `color:
v.$color-black-700;` declaration to comply with this formatting rule. The same
issue also appears at another location in the file (line 42), so apply the same
fix there as well by adding a blank line before that declaration.

Source: Linters/SAST tools

Comment thread src/lib/auth/index.ts
)
}

export default function JudgmentResult({ judgment, participants }: Props) {

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

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

이 페이지도 마찬가지로, 지금 props로 받아오고 있는데 이렇게 되면 새로고침시 데이터가 다 날라가요. 그래서
props로 넘겨주는 거보다 그냥 id를 기준으로 페이지 진입시 get API를 호출하는 것이 안전합니다.

Copy link
Copy Markdown
Collaborator Author

Choose a reason for hiding this comment

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

넵 !

import type { DisputeParticipantDto } from '@/types/dispute'
import styles from './JudgmentTypeResult.module.scss'

interface Props {

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

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

여기도 props 말고 get API!

Copy link
Copy Markdown
Collaborator Author

Choose a reason for hiding this comment

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

넵 알겠습니다 !

Comment thread src/domains/judgement/judgement.api.ts Outdated
export async function fetchJudgment(disputeId: string): Promise<AiJudgmentDto> {
const res = await fetch(`/api/disputes/${disputeId}/result`)
const json = await parseJson<AiJudgmentDto>(res, '판결 결과 조회 실패')
if (!json.success || !json.data) throw new Error(json.error?.message ?? '판결 결과 조회 실패')

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

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

에러 메세지 조금 더 친절하게 해볼까요?

wjdalss21 and others added 2 commits June 20, 2026 15:43
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
- participants nickname → name으로 변경 (DTO, route, 컴포넌트, useActiveCases)
- next.config: 카카오 HTTP 패턴 제거 (HTTPS만 허용)
- DisputePage: isCompleted null 케이스 처리 (!!dispute)
- JudgmentResult.module.scss: declaration-empty-line-before stylelint 수정
- JudgmentTypeResult.module.scss: 동일 stylelint 수정

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

Caution

Some comments are outside the diff and can’t be posted inline due to platform limitations.

⚠️ Outside diff range comments (1)
src/app/api/disputes/route.ts (1)

25-27: ⚠️ Potential issue | 🟠 Major | ⚡ Quick win

활성 사건 목록 응답에서 참여자 이름이 항상 null로 고정됩니다

Line 35에서 namenull로 고정하고, Line 26/118/237에서 user.name을 조회하지 않아 participants[].name이 실제로 채워지지 않습니다. 현재 src/hooks/useActiveCases.tsp.name을 사용하도록 바뀐 상태라, 이름 표시 요구사항이 목록 API에서 끊깁니다.

🔧 제안 수정안
 type DisputeForList = Prisma.DisputeGetPayload<{
-  include: { participants: { include: { user: { select: { profileImageUrl: true } } } } }
+  include: { participants: { include: { user: { select: { name: true; profileImageUrl: true } } } } }
 }>
 ...
 function toParticipantDto(p: DisputeForList['participants'][number]): DisputeParticipantDto {
   return {
 ...
-    name: null,
+    name: p.user.name ?? null,
     profileImageUrl: p.user.profileImageUrl ?? null,
 ...
   }
 }
 ...
       prisma.dispute.findMany({
         where,
-        include: { participants: { include: { user: { select: { profileImageUrl: true } } } } },
+        include: { participants: { include: { user: { select: { name: true, profileImageUrl: true } } } } },
 ...
       await tx.disputeParticipant.create({
         data: { disputeId: created.id, userId, role: 'ROLE_A' },
       })
       return tx.dispute.findUniqueOrThrow({
         where: { id: created.id },
-        include: { participants: { include: { user: { select: { profileImageUrl: true } } } } },
+        include: { participants: { include: { user: { select: { name: true, profileImageUrl: true } } } } },
       })

Also applies to: 35-36, 118-118, 237-237

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@src/app/api/disputes/route.ts` around lines 25 - 27, The DisputeForList type
definition does not include the user name field in its select statement, only
profileImageUrl, which means participant names are not being fetched from the
database. Additionally, the name field is being hardcoded to null on line 35
instead of being populated from the user data. Fix this by adding name: true to
the user select statement within the include object of the DisputeForList type
definition (around line 26), and then update line 35 to populate the name field
from the actual user.name value instead of null. Also verify and apply the same
fixes at lines 118 and 237 where similar issues occur.
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Outside diff comments:
In `@src/app/api/disputes/route.ts`:
- Around line 25-27: The DisputeForList type definition does not include the
user name field in its select statement, only profileImageUrl, which means
participant names are not being fetched from the database. Additionally, the
name field is being hardcoded to null on line 35 instead of being populated from
the user data. Fix this by adding name: true to the user select statement within
the include object of the DisputeForList type definition (around line 26), and
then update line 35 to populate the name field from the actual user.name value
instead of null. Also verify and apply the same fixes at lines 118 and 237 where
similar issues occur.

ℹ️ Review info
⚙️ Run configuration

Configuration used: Repository UI (base), Organization UI (inherited)

Review profile: CHILL

Plan: Pro Plus

Run ID: 438eb579-d130-4bb4-b9fc-4a75105f3bfc

📥 Commits

Reviewing files that changed from the base of the PR and between d6413b9 and 4f42530.

📒 Files selected for processing (11)
  • next.config.ts
  • src/app/(page)/disputes/[id]/page.tsx
  • src/app/api/disputes/[id]/route.ts
  • src/app/api/disputes/route.ts
  • src/components/judgement/JudgmentResult.module.scss
  • src/components/judgement/JudgmentResult.tsx
  • src/components/judgement/JudgmentTypeResult.module.scss
  • src/components/judgement/JudgmentTypeResult.tsx
  • src/hooks/useActiveCases.ts
  • src/lib/auth/index.ts
  • src/types/dispute.ts
💤 Files with no reviewable changes (1)
  • next.config.ts
✅ Files skipped from review due to trivial changes (1)
  • src/components/judgement/JudgmentResult.module.scss
🚧 Files skipped from review as they are similar to previous changes (5)
  • src/components/judgement/JudgmentTypeResult.module.scss
  • src/components/judgement/JudgmentTypeResult.tsx
  • src/components/judgement/JudgmentResult.tsx
  • src/app/(page)/disputes/[id]/page.tsx
  • src/lib/auth/index.ts

- JudgmentResult/JudgmentTypeResult: props 대신 disputeId 기반 직접 API 호출
  (새로고침 시 데이터 유실 방지, TanStack Query 캐시로 중복 요청 없음)
- DisputePage: judgment/participants props 제거, isError 기반 에러 처리
- auth/index.ts: 프로필 이미지 백필 try-catch 감싸기 (실패 시 로그인 차단 방지)
- judgement.api.ts: 에러 메시지 사용자 친화적으로 개선

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
@wjdalss21

Copy link
Copy Markdown
Collaborator Author

@evenif99 저 PR 코멘트까지 다 업데이트했습니다 !

@evenif99
evenif99 merged commit 6c80b15 into dev Jun 20, 2026
3 checks passed
@evenif99
evenif99 deleted the feature/judgement-result branch June 20, 2026 07:34
evenif99 pushed a commit that referenced this pull request Jun 20, 2026
* feat: 판결 결과 컴포넌트 및 도메인 로직 초기 작업

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* feat: 판결 결과 페이지 구현 (#판결탭/유형탭/UI)

- DisputePage: 판결/유형 서브탭(Tab 공통컴포넌트) 추가
- JudgmentResult: 이미지 기준 UI 재구성, nickname 적용
- JudgmentTypeResult: 유형탭 컴포넌트 신규 생성 (카드이미지, ActionPrompt)
- Tab.module.scss: w60 h36 사이즈 조정
- DisputeParticipantDto: nickname 필드 추가
- disputes/[id]/route: nickname 조회 추가
- judgment.mapper: cardImageUrl 추가
- types/judgment: ConflictTypeDetailDto에 cardImageUrl 추가
- auth/index: 카카오 로그인 시 profileImageUrl 저장
- page.module.scss: diaryBox max-width 제거
- NewCaseButton: AbortController timeout 30s

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* chore: next.config에 Supabase Storage 및 카카오 이미지 도메인 추가

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* fix: JudgmentResult Avatar img 태그를 next/image로 교체

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* fix: PR #90 리뷰 반영

- participants nickname → name으로 변경 (DTO, route, 컴포넌트, useActiveCases)
- next.config: 카카오 HTTP 패턴 제거 (HTTPS만 허용)
- DisputePage: isCompleted null 케이스 처리 (!!dispute)
- JudgmentResult.module.scss: declaration-empty-line-before stylelint 수정
- JudgmentTypeResult.module.scss: 동일 stylelint 수정

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* fix: PR #90 추가 리뷰 반영

- JudgmentResult/JudgmentTypeResult: props 대신 disputeId 기반 직접 API 호출
  (새로고침 시 데이터 유실 방지, TanStack Query 캐시로 중복 요청 없음)
- DisputePage: judgment/participants props 제거, isError 기반 에러 처리
- auth/index.ts: 프로필 이미지 백필 try-catch 감싸기 (실패 시 로그인 차단 방지)
- judgement.api.ts: 에러 메시지 사용자 친화적으로 개선

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* chore: 불필요한 스크린샷 PNG 파일 제거

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* refactor: CalendarRecord 모델 제거 및 EmotionDiary title 필드 추가

- CalendarRecord 모델 및 CalendarRecordType enum 제거
- User, DisputeRoom, RoomAiConversation, Dispute에서 calendarRecords relation 제거
- EmotionDiary에 title 필드 추가 (VarChar 200)

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* feat: 사건기록 페이지 API 연동

- GET /api/disputes에 completed=true 쿼리 파라미터 추가 (judged/closed 필터링)
- fetchCompletedCases, useCompletedCases 추가 (카테고리 필터 + 최신순)
- RecordListSection 더미 데이터 제거, 실제 API 연동
- 사건 박스 클릭 시 /disputes/{id}로 이동 (기존 Link 구조 유지)
- 로딩/에러/빈 상태 처리

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* feat: 사건기록 빈 상태 UI 개선

- 빈 상태 텍스트 → '등록한 사건이 없어요'
- character-case.png 이미지 + 텍스트 중앙 배치

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* feat: 사건박스 공통 컴포넌트 CaseRecordCard 분리

- CaseRecordCard 신규 생성 (src/components/ui)
- MUI AvatarGroup으로 1인/2인 참여자 프로필 겹침 표시
- RecordListSection에서 CaseRecordCard 사용하도록 교체
- 카드 스타일 RecordListSection.module.scss → CaseRecordCard.module.scss로 이동

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* fix: 카카오 CDN http 프로토콜 이미지 허용 (img1.kakaocdn.net)

카카오 기본 프로필 이미지 URL이 http로 오는 경우가 있어
*.kakaocdn.net http 패턴 추가

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* feat: 홈 페이지 배경 그라데이션 추가 (primary-200 → white)

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* fix: 홈 그라데이션 범위 15%로 조정

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* chore: dispute.hooks.ts dev 브랜치 import 충돌 사전 해결

- UseQueryOptions, DisputeDto import 추가 (dev 브랜치 기준)

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* chore: dispute.hooks.ts dev 브랜치 useDispute refetchInterval 옵션 반영

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* fix: 코드레빗 및 juacheon 리뷰 반영

- disputes/route.ts: active/completed 동시 사용 시 if/else 분기로 필터 충돌 방지
- CaseRecordCard: <time> 요소에 dateTime 속성 추가 (접근성)
- Header: transparent prop 추가, :global(header) 셀렉터 제거
- RecordListSection: 에러 메시지 구체화
- next.config.ts: 중복 HTTP 항목 제거

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

---------

Co-authored-by: Claude Sonnet 4.6 <noreply@anthropic.com>
evenif99 pushed a commit that referenced this pull request Jun 22, 2026
* feat: 판결 결과 컴포넌트 및 도메인 로직 초기 작업

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* feat: 판결 결과 페이지 구현 (#판결탭/유형탭/UI)

- DisputePage: 판결/유형 서브탭(Tab 공통컴포넌트) 추가
- JudgmentResult: 이미지 기준 UI 재구성, nickname 적용
- JudgmentTypeResult: 유형탭 컴포넌트 신규 생성 (카드이미지, ActionPrompt)
- Tab.module.scss: w60 h36 사이즈 조정
- DisputeParticipantDto: nickname 필드 추가
- disputes/[id]/route: nickname 조회 추가
- judgment.mapper: cardImageUrl 추가
- types/judgment: ConflictTypeDetailDto에 cardImageUrl 추가
- auth/index: 카카오 로그인 시 profileImageUrl 저장
- page.module.scss: diaryBox max-width 제거
- NewCaseButton: AbortController timeout 30s

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* chore: next.config에 Supabase Storage 및 카카오 이미지 도메인 추가

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* fix: JudgmentResult Avatar img 태그를 next/image로 교체

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* fix: PR #90 리뷰 반영

- participants nickname → name으로 변경 (DTO, route, 컴포넌트, useActiveCases)
- next.config: 카카오 HTTP 패턴 제거 (HTTPS만 허용)
- DisputePage: isCompleted null 케이스 처리 (!!dispute)
- JudgmentResult.module.scss: declaration-empty-line-before stylelint 수정
- JudgmentTypeResult.module.scss: 동일 stylelint 수정

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* fix: PR #90 추가 리뷰 반영

- JudgmentResult/JudgmentTypeResult: props 대신 disputeId 기반 직접 API 호출
  (새로고침 시 데이터 유실 방지, TanStack Query 캐시로 중복 요청 없음)
- DisputePage: judgment/participants props 제거, isError 기반 에러 처리
- auth/index.ts: 프로필 이미지 백필 try-catch 감싸기 (실패 시 로그인 차단 방지)
- judgement.api.ts: 에러 메시지 사용자 친화적으로 개선

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* chore: 불필요한 스크린샷 PNG 파일 제거

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* refactor: CalendarRecord 모델 제거 및 EmotionDiary title 필드 추가

- CalendarRecord 모델 및 CalendarRecordType enum 제거
- User, DisputeRoom, RoomAiConversation, Dispute에서 calendarRecords relation 제거
- EmotionDiary에 title 필드 추가 (VarChar 200)

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* feat: 사건기록 페이지 API 연동

- GET /api/disputes에 completed=true 쿼리 파라미터 추가 (judged/closed 필터링)
- fetchCompletedCases, useCompletedCases 추가 (카테고리 필터 + 최신순)
- RecordListSection 더미 데이터 제거, 실제 API 연동
- 사건 박스 클릭 시 /disputes/{id}로 이동 (기존 Link 구조 유지)
- 로딩/에러/빈 상태 처리

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* feat: 사건기록 빈 상태 UI 개선

- 빈 상태 텍스트 → '등록한 사건이 없어요'
- character-case.png 이미지 + 텍스트 중앙 배치

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* feat: 사건박스 공통 컴포넌트 CaseRecordCard 분리

- CaseRecordCard 신규 생성 (src/components/ui)
- MUI AvatarGroup으로 1인/2인 참여자 프로필 겹침 표시
- RecordListSection에서 CaseRecordCard 사용하도록 교체
- 카드 스타일 RecordListSection.module.scss → CaseRecordCard.module.scss로 이동

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* fix: 카카오 CDN http 프로토콜 이미지 허용 (img1.kakaocdn.net)

카카오 기본 프로필 이미지 URL이 http로 오는 경우가 있어
*.kakaocdn.net http 패턴 추가

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* feat: 홈 페이지 배경 그라데이션 추가 (primary-200 → white)

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* fix: 홈 그라데이션 범위 15%로 조정

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* chore: dispute.hooks.ts dev 브랜치 import 충돌 사전 해결

- UseQueryOptions, DisputeDto import 추가 (dev 브랜치 기준)

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* chore: dispute.hooks.ts dev 브랜치 useDispute refetchInterval 옵션 반영

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* fix: 코드레빗 및 juacheon 리뷰 반영

- disputes/route.ts: active/completed 동시 사용 시 if/else 분기로 필터 충돌 방지
- CaseRecordCard: <time> 요소에 dateTime 속성 추가 (접근성)
- Header: transparent prop 추가, :global(header) 셀렉터 제거
- RecordListSection: 에러 메시지 구체화
- next.config.ts: 중복 HTTP 항목 제거

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* feat: 2인 판결결과 점수 그래프 UI 수정

- isEqual/barEqual 제거, 색상 로직 ratioA >= ratioB 패턴으로 단순화
- scoreGraph margin-bottom 추가
- scoreAvatarImg 크기 명시적 fn.r(48)로 변경

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* feat: 2인 판결결과 그래프 디테일 수정

- 바 height 12 → 16, border-radius 6 → 4
- 중앙 실선 추가 (solid, border-strong, h36)
- barDark 컬러 → status-disabled-text
- scoreTitle 이름 부분만 bold 처리
- AI 고지 문구 컬러 → text-secondary

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* feat: 진술 탭 참여자 이름/MBTI 표시, 프로필 이미지 fallback 개선

- 진술 카드 레이블 A/B → 참여자 실명으로 변경
- 진술 카드 하단 프로필 이미지 + MBTI 추가
- DisputeParticipantDto에 mbti 필드 추가
- API participants에 mbti 포함 (disputes/[id] GET/PATCH)
- profileImageUrl null 시 image 필드 fallback 적용 (목록/상세 API)
- DisputePage.module.scss mixins import 추가
- JudgmentResult 그래프 점선/바 높이 디테일 수정

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* feat: JudgmentResult 참여자 이름 변수 통일 및 텍스트 치환 적용

- nameA / nameB 변수로 cardLabel, barLabel 통일
- replaceRoleNames 함수로 aFault/bFault/aSuggestedLine/bSuggestedLine 내 A님→실제이름 치환

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* fix: 코드레빗 리뷰 반영

- replaceRoleNames 단일 패스 치환으로 개선 (A님|B님 alternation)
- disputes 목록/POST API Prisma 쿼리에 image 필드 선택 추가

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

---------

Co-authored-by: Claude Sonnet 4.6 <noreply@anthropic.com>
evenif99 pushed a commit that referenced this pull request Jun 22, 2026
* feat: 판결 결과 컴포넌트 및 도메인 로직 초기 작업

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* feat: 판결 결과 페이지 구현 (#판결탭/유형탭/UI)

- DisputePage: 판결/유형 서브탭(Tab 공통컴포넌트) 추가
- JudgmentResult: 이미지 기준 UI 재구성, nickname 적용
- JudgmentTypeResult: 유형탭 컴포넌트 신규 생성 (카드이미지, ActionPrompt)
- Tab.module.scss: w60 h36 사이즈 조정
- DisputeParticipantDto: nickname 필드 추가
- disputes/[id]/route: nickname 조회 추가
- judgment.mapper: cardImageUrl 추가
- types/judgment: ConflictTypeDetailDto에 cardImageUrl 추가
- auth/index: 카카오 로그인 시 profileImageUrl 저장
- page.module.scss: diaryBox max-width 제거
- NewCaseButton: AbortController timeout 30s

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* chore: next.config에 Supabase Storage 및 카카오 이미지 도메인 추가

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* fix: JudgmentResult Avatar img 태그를 next/image로 교체

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* fix: PR #90 리뷰 반영

- participants nickname → name으로 변경 (DTO, route, 컴포넌트, useActiveCases)
- next.config: 카카오 HTTP 패턴 제거 (HTTPS만 허용)
- DisputePage: isCompleted null 케이스 처리 (!!dispute)
- JudgmentResult.module.scss: declaration-empty-line-before stylelint 수정
- JudgmentTypeResult.module.scss: 동일 stylelint 수정

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* fix: PR #90 추가 리뷰 반영

- JudgmentResult/JudgmentTypeResult: props 대신 disputeId 기반 직접 API 호출
  (새로고침 시 데이터 유실 방지, TanStack Query 캐시로 중복 요청 없음)
- DisputePage: judgment/participants props 제거, isError 기반 에러 처리
- auth/index.ts: 프로필 이미지 백필 try-catch 감싸기 (실패 시 로그인 차단 방지)
- judgement.api.ts: 에러 메시지 사용자 친화적으로 개선

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* chore: 불필요한 스크린샷 PNG 파일 제거

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* refactor: CalendarRecord 모델 제거 및 EmotionDiary title 필드 추가

- CalendarRecord 모델 및 CalendarRecordType enum 제거
- User, DisputeRoom, RoomAiConversation, Dispute에서 calendarRecords relation 제거
- EmotionDiary에 title 필드 추가 (VarChar 200)

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* feat: 사건기록 페이지 API 연동

- GET /api/disputes에 completed=true 쿼리 파라미터 추가 (judged/closed 필터링)
- fetchCompletedCases, useCompletedCases 추가 (카테고리 필터 + 최신순)
- RecordListSection 더미 데이터 제거, 실제 API 연동
- 사건 박스 클릭 시 /disputes/{id}로 이동 (기존 Link 구조 유지)
- 로딩/에러/빈 상태 처리

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* feat: 사건기록 빈 상태 UI 개선

- 빈 상태 텍스트 → '등록한 사건이 없어요'
- character-case.png 이미지 + 텍스트 중앙 배치

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* feat: 사건박스 공통 컴포넌트 CaseRecordCard 분리

- CaseRecordCard 신규 생성 (src/components/ui)
- MUI AvatarGroup으로 1인/2인 참여자 프로필 겹침 표시
- RecordListSection에서 CaseRecordCard 사용하도록 교체
- 카드 스타일 RecordListSection.module.scss → CaseRecordCard.module.scss로 이동

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* fix: 카카오 CDN http 프로토콜 이미지 허용 (img1.kakaocdn.net)

카카오 기본 프로필 이미지 URL이 http로 오는 경우가 있어
*.kakaocdn.net http 패턴 추가

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* feat: 홈 페이지 배경 그라데이션 추가 (primary-200 → white)

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* fix: 홈 그라데이션 범위 15%로 조정

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* chore: dispute.hooks.ts dev 브랜치 import 충돌 사전 해결

- UseQueryOptions, DisputeDto import 추가 (dev 브랜치 기준)

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* chore: dispute.hooks.ts dev 브랜치 useDispute refetchInterval 옵션 반영

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* fix: 코드레빗 및 juacheon 리뷰 반영

- disputes/route.ts: active/completed 동시 사용 시 if/else 분기로 필터 충돌 방지
- CaseRecordCard: <time> 요소에 dateTime 속성 추가 (접근성)
- Header: transparent prop 추가, :global(header) 셀렉터 제거
- RecordListSection: 에러 메시지 구체화
- next.config.ts: 중복 HTTP 항목 제거

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* feat: 2인 판결결과 점수 그래프 UI 수정

- isEqual/barEqual 제거, 색상 로직 ratioA >= ratioB 패턴으로 단순화
- scoreGraph margin-bottom 추가
- scoreAvatarImg 크기 명시적 fn.r(48)로 변경

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* feat: 2인 판결결과 그래프 디테일 수정

- 바 height 12 → 16, border-radius 6 → 4
- 중앙 실선 추가 (solid, border-strong, h36)
- barDark 컬러 → status-disabled-text
- scoreTitle 이름 부분만 bold 처리
- AI 고지 문구 컬러 → text-secondary

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* feat: 진술 탭 참여자 이름/MBTI 표시, 프로필 이미지 fallback 개선

- 진술 카드 레이블 A/B → 참여자 실명으로 변경
- 진술 카드 하단 프로필 이미지 + MBTI 추가
- DisputeParticipantDto에 mbti 필드 추가
- API participants에 mbti 포함 (disputes/[id] GET/PATCH)
- profileImageUrl null 시 image 필드 fallback 적용 (목록/상세 API)
- DisputePage.module.scss mixins import 추가
- JudgmentResult 그래프 점선/바 높이 디테일 수정

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* feat: JudgmentResult 참여자 이름 변수 통일 및 텍스트 치환 적용

- nameA / nameB 변수로 cardLabel, barLabel 통일
- replaceRoleNames 함수로 aFault/bFault/aSuggestedLine/bSuggestedLine 내 A님→실제이름 치환

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* fix: 코드레빗 리뷰 반영

- replaceRoleNames 단일 패스 치환으로 개선 (A님|B님 alternation)
- disputes 목록/POST API Prisma 쿼리에 image 필드 선택 추가

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* perf: statistics/categories API 빌드 시 DB 호출 제거

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* feat: 카테고리 사건 2개 제한 및 사건기록 무한스크롤

- POST /api/rooms 카테고리당 진행중 사건 2개 초과 시 CATEGORY_LIMIT_EXCEEDED(422) 반환
- DisputeListResponse에 hasNext 필드 추가
- fetchCompletedCases 페이지 기반 API 호출로 전환 (limit 10)
- useCompletedCases useInfiniteQuery로 전환
- RecordListSection IntersectionObserver 기반 무한스크롤 구현
- 모든 데이터 로드 시 '모든 데이터를 불러왔습니다' 표시
- NewCaseButton 카테고리 한도 초과 시 에러 모달 표시

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* fix: 코드레빗 리뷰 반영

- GET /api/disputes: completed 파라미터 where 조건 반영으로 hasNext 정확도 개선
- POST /api/disputes: 카테고리 한도 체크 추가 (직접 API 호출 우회 방지)
- NewCaseButton: limitError 모달 표시 시 body 스크롤 잠금 처리

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* fix: 카테고리 한도 초과 에러 모달 UI 개선

- 기존 카테고리 패널 스타일 재사용 → 독립 검은 배경 센터 모달로 변경
- limitOverlay, limitModal, limitMessage, limitCloseButton 스타일 추가

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* fix: 카테고리 한도 에러 모달 메시지 줄바꿈 적용

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

---------

Co-authored-by: Claude Sonnet 4.6 <noreply@anthropic.com>
evenif99 pushed a commit that referenced this pull request Jun 23, 2026
* feat: 판결 결과 컴포넌트 및 도메인 로직 초기 작업

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* feat: 판결 결과 페이지 구현 (#판결탭/유형탭/UI)

- DisputePage: 판결/유형 서브탭(Tab 공통컴포넌트) 추가
- JudgmentResult: 이미지 기준 UI 재구성, nickname 적용
- JudgmentTypeResult: 유형탭 컴포넌트 신규 생성 (카드이미지, ActionPrompt)
- Tab.module.scss: w60 h36 사이즈 조정
- DisputeParticipantDto: nickname 필드 추가
- disputes/[id]/route: nickname 조회 추가
- judgment.mapper: cardImageUrl 추가
- types/judgment: ConflictTypeDetailDto에 cardImageUrl 추가
- auth/index: 카카오 로그인 시 profileImageUrl 저장
- page.module.scss: diaryBox max-width 제거
- NewCaseButton: AbortController timeout 30s

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* chore: next.config에 Supabase Storage 및 카카오 이미지 도메인 추가

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* fix: JudgmentResult Avatar img 태그를 next/image로 교체

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* fix: PR #90 리뷰 반영

- participants nickname → name으로 변경 (DTO, route, 컴포넌트, useActiveCases)
- next.config: 카카오 HTTP 패턴 제거 (HTTPS만 허용)
- DisputePage: isCompleted null 케이스 처리 (!!dispute)
- JudgmentResult.module.scss: declaration-empty-line-before stylelint 수정
- JudgmentTypeResult.module.scss: 동일 stylelint 수정

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* fix: PR #90 추가 리뷰 반영

- JudgmentResult/JudgmentTypeResult: props 대신 disputeId 기반 직접 API 호출
  (새로고침 시 데이터 유실 방지, TanStack Query 캐시로 중복 요청 없음)
- DisputePage: judgment/participants props 제거, isError 기반 에러 처리
- auth/index.ts: 프로필 이미지 백필 try-catch 감싸기 (실패 시 로그인 차단 방지)
- judgement.api.ts: 에러 메시지 사용자 친화적으로 개선

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* chore: 불필요한 스크린샷 PNG 파일 제거

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* refactor: CalendarRecord 모델 제거 및 EmotionDiary title 필드 추가

- CalendarRecord 모델 및 CalendarRecordType enum 제거
- User, DisputeRoom, RoomAiConversation, Dispute에서 calendarRecords relation 제거
- EmotionDiary에 title 필드 추가 (VarChar 200)

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* feat: 사건기록 페이지 API 연동

- GET /api/disputes에 completed=true 쿼리 파라미터 추가 (judged/closed 필터링)
- fetchCompletedCases, useCompletedCases 추가 (카테고리 필터 + 최신순)
- RecordListSection 더미 데이터 제거, 실제 API 연동
- 사건 박스 클릭 시 /disputes/{id}로 이동 (기존 Link 구조 유지)
- 로딩/에러/빈 상태 처리

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* feat: 사건기록 빈 상태 UI 개선

- 빈 상태 텍스트 → '등록한 사건이 없어요'
- character-case.png 이미지 + 텍스트 중앙 배치

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* feat: 사건박스 공통 컴포넌트 CaseRecordCard 분리

- CaseRecordCard 신규 생성 (src/components/ui)
- MUI AvatarGroup으로 1인/2인 참여자 프로필 겹침 표시
- RecordListSection에서 CaseRecordCard 사용하도록 교체
- 카드 스타일 RecordListSection.module.scss → CaseRecordCard.module.scss로 이동

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* fix: 카카오 CDN http 프로토콜 이미지 허용 (img1.kakaocdn.net)

카카오 기본 프로필 이미지 URL이 http로 오는 경우가 있어
*.kakaocdn.net http 패턴 추가

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* feat: 홈 페이지 배경 그라데이션 추가 (primary-200 → white)

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* fix: 홈 그라데이션 범위 15%로 조정

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* chore: dispute.hooks.ts dev 브랜치 import 충돌 사전 해결

- UseQueryOptions, DisputeDto import 추가 (dev 브랜치 기준)

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* chore: dispute.hooks.ts dev 브랜치 useDispute refetchInterval 옵션 반영

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* fix: 코드레빗 및 juacheon 리뷰 반영

- disputes/route.ts: active/completed 동시 사용 시 if/else 분기로 필터 충돌 방지
- CaseRecordCard: <time> 요소에 dateTime 속성 추가 (접근성)
- Header: transparent prop 추가, :global(header) 셀렉터 제거
- RecordListSection: 에러 메시지 구체화
- next.config.ts: 중복 HTTP 항목 제거

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* feat: 2인 판결결과 점수 그래프 UI 수정

- isEqual/barEqual 제거, 색상 로직 ratioA >= ratioB 패턴으로 단순화
- scoreGraph margin-bottom 추가
- scoreAvatarImg 크기 명시적 fn.r(48)로 변경

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* feat: 2인 판결결과 그래프 디테일 수정

- 바 height 12 → 16, border-radius 6 → 4
- 중앙 실선 추가 (solid, border-strong, h36)
- barDark 컬러 → status-disabled-text
- scoreTitle 이름 부분만 bold 처리
- AI 고지 문구 컬러 → text-secondary

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* feat: 진술 탭 참여자 이름/MBTI 표시, 프로필 이미지 fallback 개선

- 진술 카드 레이블 A/B → 참여자 실명으로 변경
- 진술 카드 하단 프로필 이미지 + MBTI 추가
- DisputeParticipantDto에 mbti 필드 추가
- API participants에 mbti 포함 (disputes/[id] GET/PATCH)
- profileImageUrl null 시 image 필드 fallback 적용 (목록/상세 API)
- DisputePage.module.scss mixins import 추가
- JudgmentResult 그래프 점선/바 높이 디테일 수정

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* feat: JudgmentResult 참여자 이름 변수 통일 및 텍스트 치환 적용

- nameA / nameB 변수로 cardLabel, barLabel 통일
- replaceRoleNames 함수로 aFault/bFault/aSuggestedLine/bSuggestedLine 내 A님→실제이름 치환

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* fix: 코드레빗 리뷰 반영

- replaceRoleNames 단일 패스 치환으로 개선 (A님|B님 alternation)
- disputes 목록/POST API Prisma 쿼리에 image 필드 선택 추가

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* perf: statistics/categories API 빌드 시 DB 호출 제거

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* feat: 카테고리 사건 2개 제한 및 사건기록 무한스크롤

- POST /api/rooms 카테고리당 진행중 사건 2개 초과 시 CATEGORY_LIMIT_EXCEEDED(422) 반환
- DisputeListResponse에 hasNext 필드 추가
- fetchCompletedCases 페이지 기반 API 호출로 전환 (limit 10)
- useCompletedCases useInfiniteQuery로 전환
- RecordListSection IntersectionObserver 기반 무한스크롤 구현
- 모든 데이터 로드 시 '모든 데이터를 불러왔습니다' 표시
- NewCaseButton 카테고리 한도 초과 시 에러 모달 표시

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* fix: 코드레빗 리뷰 반영

- GET /api/disputes: completed 파라미터 where 조건 반영으로 hasNext 정확도 개선
- POST /api/disputes: 카테고리 한도 체크 추가 (직접 API 호출 우회 방지)
- NewCaseButton: limitError 모달 표시 시 body 스크롤 잠금 처리

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* fix: 카테고리 한도 초과 에러 모달 UI 개선

- 기존 카테고리 패널 스타일 재사용 → 독립 검은 배경 센터 모달로 변경
- limitOverlay, limitModal, limitMessage, limitCloseButton 스타일 추가

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* fix: 카테고리 한도 에러 모달 메시지 줄바꿈 적용

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* fix: 홈 통계 staleTime 24시간 → 1시간으로 단축

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* feat: 갈등유형 공유 페이지 분리 및 URL 공유 기능 구현

- /disputes/[id]/type 갈등유형 전용 페이지 신규 생성 (비회원 접근 가능)
- GET /api/disputes/[id]/conflict-type 공개 API 추가 (유형명·이미지 URL만 반환)
- 미들웨어에서 /disputes/[id]/type 인증 예외 처리
- 카카오 공유 → URL 복사(PC) / Web Share API(모바일) 방식으로 변경
- generateMetadata로 OG 메타 태그 생성 (og:image에 cardImageUrl 적용)
- root layout에 metadataBase 추가

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* feat: 갈등유형 결과 이미지 다운로드 기능 구현

- ConflictTypeClient, JudgmentTypeResult 결과 다운받기 버튼 활성화
- Supabase Storage 이미지 fetch 후 Blob 변환으로 로컬 저장
- fetch 실패(CORS 등) 시 새 탭으로 열어 수동 저장 유도

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* fix: metadataBase에 VERCEL_URL fallback 추가

- 배포 환경에서 NEXT_PUBLIC_BASE_URL 미설정 시 VERCEL_URL을 자동 감지하여 사용

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* fix: ConflictTypeDetail Prisma 필드명 card_image_url로 수정

- cardImageUrl은 @Map 없이 card_image_url로 정의된 필드
- select 및 반환 시 camelCase 변환 처리

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* fix: JudgmentTypeResult에 disputeId prop 전달 추가

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* fix: ConflictTypeClient data null 체크 옵셔널 체이닝 적용

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* fix: 코드레빗 리뷰 반영 (res.ok 체크, SCSS 린트, 에러 로그, Kakao SDK 제거)

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* fix: 갈등 유형 탭 이름 표시를 role_a 고정에서 현재 사용자 기준으로 수정

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* fix: session.user.id 타입 오류 수정 및 유형 탭 이름 표시 fallback 처리

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

---------

Co-authored-by: Claude Sonnet 4.6 <noreply@anthropic.com>
evenif99 pushed a commit that referenced this pull request Jun 23, 2026
* feat: 판결 결과 컴포넌트 및 도메인 로직 초기 작업

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* feat: 판결 결과 페이지 구현 (#판결탭/유형탭/UI)

- DisputePage: 판결/유형 서브탭(Tab 공통컴포넌트) 추가
- JudgmentResult: 이미지 기준 UI 재구성, nickname 적용
- JudgmentTypeResult: 유형탭 컴포넌트 신규 생성 (카드이미지, ActionPrompt)
- Tab.module.scss: w60 h36 사이즈 조정
- DisputeParticipantDto: nickname 필드 추가
- disputes/[id]/route: nickname 조회 추가
- judgment.mapper: cardImageUrl 추가
- types/judgment: ConflictTypeDetailDto에 cardImageUrl 추가
- auth/index: 카카오 로그인 시 profileImageUrl 저장
- page.module.scss: diaryBox max-width 제거
- NewCaseButton: AbortController timeout 30s

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* chore: next.config에 Supabase Storage 및 카카오 이미지 도메인 추가

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* fix: JudgmentResult Avatar img 태그를 next/image로 교체

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* fix: PR #90 리뷰 반영

- participants nickname → name으로 변경 (DTO, route, 컴포넌트, useActiveCases)
- next.config: 카카오 HTTP 패턴 제거 (HTTPS만 허용)
- DisputePage: isCompleted null 케이스 처리 (!!dispute)
- JudgmentResult.module.scss: declaration-empty-line-before stylelint 수정
- JudgmentTypeResult.module.scss: 동일 stylelint 수정

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* fix: PR #90 추가 리뷰 반영

- JudgmentResult/JudgmentTypeResult: props 대신 disputeId 기반 직접 API 호출
  (새로고침 시 데이터 유실 방지, TanStack Query 캐시로 중복 요청 없음)
- DisputePage: judgment/participants props 제거, isError 기반 에러 처리
- auth/index.ts: 프로필 이미지 백필 try-catch 감싸기 (실패 시 로그인 차단 방지)
- judgement.api.ts: 에러 메시지 사용자 친화적으로 개선

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* chore: 불필요한 스크린샷 PNG 파일 제거

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* refactor: CalendarRecord 모델 제거 및 EmotionDiary title 필드 추가

- CalendarRecord 모델 및 CalendarRecordType enum 제거
- User, DisputeRoom, RoomAiConversation, Dispute에서 calendarRecords relation 제거
- EmotionDiary에 title 필드 추가 (VarChar 200)

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* feat: 사건기록 페이지 API 연동

- GET /api/disputes에 completed=true 쿼리 파라미터 추가 (judged/closed 필터링)
- fetchCompletedCases, useCompletedCases 추가 (카테고리 필터 + 최신순)
- RecordListSection 더미 데이터 제거, 실제 API 연동
- 사건 박스 클릭 시 /disputes/{id}로 이동 (기존 Link 구조 유지)
- 로딩/에러/빈 상태 처리

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* feat: 사건기록 빈 상태 UI 개선

- 빈 상태 텍스트 → '등록한 사건이 없어요'
- character-case.png 이미지 + 텍스트 중앙 배치

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* feat: 사건박스 공통 컴포넌트 CaseRecordCard 분리

- CaseRecordCard 신규 생성 (src/components/ui)
- MUI AvatarGroup으로 1인/2인 참여자 프로필 겹침 표시
- RecordListSection에서 CaseRecordCard 사용하도록 교체
- 카드 스타일 RecordListSection.module.scss → CaseRecordCard.module.scss로 이동

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* fix: 카카오 CDN http 프로토콜 이미지 허용 (img1.kakaocdn.net)

카카오 기본 프로필 이미지 URL이 http로 오는 경우가 있어
*.kakaocdn.net http 패턴 추가

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* feat: 홈 페이지 배경 그라데이션 추가 (primary-200 → white)

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* fix: 홈 그라데이션 범위 15%로 조정

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* chore: dispute.hooks.ts dev 브랜치 import 충돌 사전 해결

- UseQueryOptions, DisputeDto import 추가 (dev 브랜치 기준)

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* chore: dispute.hooks.ts dev 브랜치 useDispute refetchInterval 옵션 반영

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* fix: 코드레빗 및 juacheon 리뷰 반영

- disputes/route.ts: active/completed 동시 사용 시 if/else 분기로 필터 충돌 방지
- CaseRecordCard: <time> 요소에 dateTime 속성 추가 (접근성)
- Header: transparent prop 추가, :global(header) 셀렉터 제거
- RecordListSection: 에러 메시지 구체화
- next.config.ts: 중복 HTTP 항목 제거

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* feat: 2인 판결결과 점수 그래프 UI 수정

- isEqual/barEqual 제거, 색상 로직 ratioA >= ratioB 패턴으로 단순화
- scoreGraph margin-bottom 추가
- scoreAvatarImg 크기 명시적 fn.r(48)로 변경

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* feat: 2인 판결결과 그래프 디테일 수정

- 바 height 12 → 16, border-radius 6 → 4
- 중앙 실선 추가 (solid, border-strong, h36)
- barDark 컬러 → status-disabled-text
- scoreTitle 이름 부분만 bold 처리
- AI 고지 문구 컬러 → text-secondary

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* feat: 진술 탭 참여자 이름/MBTI 표시, 프로필 이미지 fallback 개선

- 진술 카드 레이블 A/B → 참여자 실명으로 변경
- 진술 카드 하단 프로필 이미지 + MBTI 추가
- DisputeParticipantDto에 mbti 필드 추가
- API participants에 mbti 포함 (disputes/[id] GET/PATCH)
- profileImageUrl null 시 image 필드 fallback 적용 (목록/상세 API)
- DisputePage.module.scss mixins import 추가
- JudgmentResult 그래프 점선/바 높이 디테일 수정

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* feat: JudgmentResult 참여자 이름 변수 통일 및 텍스트 치환 적용

- nameA / nameB 변수로 cardLabel, barLabel 통일
- replaceRoleNames 함수로 aFault/bFault/aSuggestedLine/bSuggestedLine 내 A님→실제이름 치환

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* fix: 코드레빗 리뷰 반영

- replaceRoleNames 단일 패스 치환으로 개선 (A님|B님 alternation)
- disputes 목록/POST API Prisma 쿼리에 image 필드 선택 추가

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* perf: statistics/categories API 빌드 시 DB 호출 제거

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* feat: 카테고리 사건 2개 제한 및 사건기록 무한스크롤

- POST /api/rooms 카테고리당 진행중 사건 2개 초과 시 CATEGORY_LIMIT_EXCEEDED(422) 반환
- DisputeListResponse에 hasNext 필드 추가
- fetchCompletedCases 페이지 기반 API 호출로 전환 (limit 10)
- useCompletedCases useInfiniteQuery로 전환
- RecordListSection IntersectionObserver 기반 무한스크롤 구현
- 모든 데이터 로드 시 '모든 데이터를 불러왔습니다' 표시
- NewCaseButton 카테고리 한도 초과 시 에러 모달 표시

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* fix: 코드레빗 리뷰 반영

- GET /api/disputes: completed 파라미터 where 조건 반영으로 hasNext 정확도 개선
- POST /api/disputes: 카테고리 한도 체크 추가 (직접 API 호출 우회 방지)
- NewCaseButton: limitError 모달 표시 시 body 스크롤 잠금 처리

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* fix: 카테고리 한도 초과 에러 모달 UI 개선

- 기존 카테고리 패널 스타일 재사용 → 독립 검은 배경 센터 모달로 변경
- limitOverlay, limitModal, limitMessage, limitCloseButton 스타일 추가

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* fix: 카테고리 한도 에러 모달 메시지 줄바꿈 적용

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* fix: 홈 통계 staleTime 24시간 → 1시간으로 단축

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* feat: 갈등유형 공유 페이지 분리 및 URL 공유 기능 구현

- /disputes/[id]/type 갈등유형 전용 페이지 신규 생성 (비회원 접근 가능)
- GET /api/disputes/[id]/conflict-type 공개 API 추가 (유형명·이미지 URL만 반환)
- 미들웨어에서 /disputes/[id]/type 인증 예외 처리
- 카카오 공유 → URL 복사(PC) / Web Share API(모바일) 방식으로 변경
- generateMetadata로 OG 메타 태그 생성 (og:image에 cardImageUrl 적용)
- root layout에 metadataBase 추가

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* feat: 갈등유형 결과 이미지 다운로드 기능 구현

- ConflictTypeClient, JudgmentTypeResult 결과 다운받기 버튼 활성화
- Supabase Storage 이미지 fetch 후 Blob 변환으로 로컬 저장
- fetch 실패(CORS 등) 시 새 탭으로 열어 수동 저장 유도

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* fix: metadataBase에 VERCEL_URL fallback 추가

- 배포 환경에서 NEXT_PUBLIC_BASE_URL 미설정 시 VERCEL_URL을 자동 감지하여 사용

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* fix: ConflictTypeDetail Prisma 필드명 card_image_url로 수정

- cardImageUrl은 @Map 없이 card_image_url로 정의된 필드
- select 및 반환 시 camelCase 변환 처리

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* fix: JudgmentTypeResult에 disputeId prop 전달 추가

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* fix: ConflictTypeClient data null 체크 옵셔널 체이닝 적용

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* fix: 코드레빗 리뷰 반영 (res.ok 체크, SCSS 린트, 에러 로그, Kakao SDK 제거)

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* fix: 갈등 유형 탭 이름 표시를 role_a 고정에서 현재 사용자 기준으로 수정

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* fix: session.user.id 타입 오류 수정 및 유형 탭 이름 표시 fallback 처리

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* fix: PR #124 리뷰 반영 - ConflictTypeClient 에러 상태 뒤로가기, 타이틀 개인화, 비로그인 버튼 경로 수정

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* fix: 새 사건 카테고리 패널 딤 배경 적용, 에러 알림 모달로 변경, 홈 캐릭터 이미지 위치 조정

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* fix: closed 상태 판결 결과 미로드, 기본 이미지 확장자 통일, replaceRoleNames 순서 버그 수정

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

* fix: 갈등 유형 카드 이미지 max-width 360px 제한 적용

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

---------

Co-authored-by: Claude Sonnet 4.6 <noreply@anthropic.com>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants