Skip to content

Conversation

@seongjunnoh
Copy link
Collaborator

@seongjunnoh seongjunnoh commented Sep 25, 2025

#️⃣ 연관된 이슈

closes #314

📝 작업 내용

FE 분들의 요청을 받아 '알림 읽음 처리 api' 의 응답으로 반환하는 데이터들의 구조를 수정했습니다.

  1. 모임방 기록 route 경로를 ROOM_POST_DETAIL 1개로 통일
  • 기존에 있던 ROOM_RECORD_DETAIL, ROOM_VOTE_DETAIL 을 삭제하고 모두 ROOM_POST_DETAIL 로 통일시켰습니다
  1. ROOM_POST_DETAIL route 시에 param에 "openComments" 키 추가
  • 알림 클릭 시 댓글 모달창이 열린 채로 화면 전환이 이루어져야 하는 경우를 위해 "openComments" key 를 추가했습니다.
  • value 를 boolean type 으로 구성해서, FE 분들은 이 값으로 댓글 모달창을 열지 말지를 판단할 수 있습니다

📸 스크린샷

image image

-> 댓글 모달창이 열려야하는 경우에 대해 response.params.openComments 값이 true 인 것 확인했습니다

💬 리뷰 요구사항

리뷰어가 특별히 봐주었으면 하는 부분이 있다면 작성해주세요

📌 PR 진행 시 이러한 점들을 참고해 주세요

* P1 : 꼭 반영해 주세요 (Request Changes) - 이슈가 발생하거나 취약점이 발견되는 케이스 등
* P2 : 반영을 적극적으로 고려해 주시면 좋을 것 같아요 (Comment)
* P3 : 이런 방법도 있을 것 같아요~ 등의 사소한 의견입니다 (Chore)

Summary by CodeRabbit

  • 신기능
    • 알림에서 댓글/답글 알림을 탭하면 해당 게시글이 열리고 댓글 영역이 즉시 표시됩니다.
  • 변경사항
    • 룸 게시글 검색의 기본 페이지 크기를 10에서 20으로 확대해 한 화면에서 더 많은 게시글을 볼 수 있습니다.
  • 리팩터
    • 알림 처리 로직을 일원화해 게시글 유형에 따른 알림 동작의 일관성과 안정성을 개선했습니다.

@seongjunnoh seongjunnoh linked an issue Sep 25, 2025 that may be closed by this pull request
2 tasks
@coderabbitai
Copy link

coderabbitai bot commented Sep 25, 2025

Walkthrough

알림 관련 서비스 전반에서 postType 처리를 String 비교에서 PostType enum 기반 switch로 전환하고, Room 알림 오케스트레이터의 시그니처를 PostType으로 변경했다. Room 리다이렉트 스펙 생성 로직을 헬퍼 메서드로 분리했고, MessageRoute에서 ROOM_RECORD_DETAIL/ROOM_VOTE_DETAIL을 제거했다. 기본 페이지 사이즈를 20으로 상향했다.

Changes

Cohort / File(s) Change Summary
Comment notification dispatch
src/main/java/konkuk/thip/comment/application/service/CommentCreateService.java, src/main/java/konkuk/thip/comment/application/service/CommentLikeService.java
postType 분기 if-else → PostType enum 기반 switch. FEED는 feed 알림, RECORD/VOTE는 room 알림 호출로 정리. 호출 시 postType 인자 enum 사용.
Room notification orchestrator API
src/main/java/konkuk/thip/notification/application/port/in/RoomNotificationOrchestrator.java
공개 메서드 4곳의 파라미터 타입 변경: postType String → PostType.
Room notification orchestrator impl & redirect spec
src/main/java/konkuk/thip/notification/application/service/RoomNotificationOrchestratorSyncImpl.java
구현체 메서드들의 postType 타입 변경(String → PostType). 리다이렉트 스펙 생성 로직을 createRoomPostWithCommentsRedirectSpec/createRoomPostRedirectSpec 헬퍼로 분리하고 사용.
Domain route enum cleanup
src/main/java/konkuk/thip/notification/domain/value/MessageRoute.java
ROOM_RECORD_DETAIL, ROOM_VOTE_DETAIL 제거. ROOM_POST_DETAIL 하나로 통합(구분은 PostType으로 처리).
Post like notification dispatch
src/main/java/konkuk/thip/post/application/service/PostLikeService.java
알림 분기 if-else → PostType 기반 switch로 단순화. FEED/RECORD/VOTE별 호출 대상 정리 및 enum 전달.
Persistence import cleanup
src/main/java/konkuk/thip/post/adapter/out/persistence/PostLikeCommandPersistenceAdapter.java
미사용 import 제거, 정적 import 추가. 기능 변경 없음.
Room post search paging
src/main/java/konkuk/thip/roompost/application/service/RoomPostSearchService.java
DEFAULT_PAGE_SIZE 10 → 20.
Tests updated for typed PostType
src/test/java/konkuk/thip/notification/application/service/RoomNotificationOrchestratorSyncImplTest.java, .../RoomNotificationOrchestratorSyncImplUnitTest.java
테스트 내 postType 사용을 String → PostType enum으로 변경하여 시그니처 변경 반영.

Sequence Diagram(s)

sequenceDiagram
  autonumber
  actor User as User
  participant CS as CommentCreateService
  participant CLS as CommentLikeService
  participant PLS as PostLikeService
  participant FNO as FeedNotificationOrchestrator
  participant RNO as RoomNotificationOrchestrator

  rect rgba(230,245,255,0.6)
  note over CS: 댓글 작성
  User->>CS: createComment()
  CS->>CS: PostType.from(...)
  alt postType == FEED
    CS->>FNO: notifyFeedCommented(postId)
  else postType == RECORD/VOTE
    CS->>RNO: notifyRoomPostCommented(roomId, page, postId, PostType)
  end
  end

  rect rgba(240,255,230,0.6)
  note over CLS: 댓글 좋아요
  User->>CLS: likeComment()
  CLS->>CLS: PostType.from(...)
  alt FEED
    CLS->>FNO: notifyFeedCommentLiked(postId)
  else RECORD/VOTE
    CLS->>RNO: notifyRoomCommentLiked(roomId, page, postId, PostType)
  end
  end

  rect rgba(255,245,230,0.6)
  note over PLS: 게시글 좋아요
  User->>PLS: likePost()
  PLS->>PLS: PostType.from(...)
  alt FEED
    PLS->>FNO: notifyFeedLiked(postId)
  else RECORD/VOTE
    PLS->>RNO: notifyRoomPostLiked(roomId, page, postId, PostType)
  end
  end
Loading
sequenceDiagram
  participant RNOI as RoomNotificationOrchestratorSyncImpl
  participant N as NotificationService
  note over RNOI: 리다이렉트 스펙 생성 방식 변경
  RNOI->>RNOI: createRoomPostWithCommentsRedirectSpec(...) / createRoomPostRedirectSpec(...)
  RNOI->>N: send(notification, redirectSpec{ openComments: true/false, postType })
Loading

Estimated code review effort

🎯 3 (Moderate) | ⏱️ ~25 minutes

Possibly related PRs

Suggested labels

🍀 refactor, 👻 성준

Suggested reviewers

  • hd0rable
  • buzz0331

Poem

토끼는 귀 쫑긋, PostType 탁!
문자열 숲 지나 enum 길로 왔딱!
알림 길잡이, 리다이렉트 꽉꽉,
댓글도 좋아요도 딱딱 맞닥.
ROUTE는 하나로 깔끔히 정착 — 깡총!

Pre-merge checks and finishing touches

❌ Failed checks (2 warnings)
Check name Status Explanation Resolution
Out of Scope Changes Check ⚠️ Warning PR에 notification redirect 구조 변경과 무관하게 RoomPostSearchService의 기본 페이지 크기를 10에서 20으로 조정한 변경사항과 PostLikeCommandPersistenceAdapter의 import 정리 같은 수정이 포함되어 있어 이슈 #314의 범위를 벗어납니다. notification redirect 관련 변경만 별도의 PR로 남기고 RoomPostSearchService의 페이지 크기 변경과 import 정리 부분은 분리하거나 제거하여 이 PR이 이슈 #314 범위에 집중하도록 수정해 주세요.
Docstring Coverage ⚠️ Warning Docstring coverage is 8.33% which is insufficient. The required threshold is 80.00%. You can run @coderabbitai generate docstrings to improve docstring coverage.
✅ Passed checks (3 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title Check ✅ Passed 제목은 알림 리다이렉트를 위한 데이터 구조 수정을 주요 변경점으로 명확히 요약하고 있어 PR의 핵심 내용을 정확히 반영합니다. 불필요한 파일 목록이나 이모지 없이 간결하여 팀원이 히스토리에서 빠르게 이해할 수 있습니다.
Linked Issues Check ✅ Passed PR은 프론트엔드 요구사항에 따라 notification redirect API의 response 데이터 구조를 변경하고 ROOM_POST_DETAIL로 경로를 통합했으며 openComments boolean을 추가하여 이슈 #314의 모든 요구사항을 충족합니다. 특히 private helper 메서드를 도입해 일관성 있는 redirect spec을 생성하고 관련 인터페이스 시그니처를 수정한 점이 프론트엔드 연동을 위한 변경사항을 완전하게 구현함을 보여줍니다.
✨ Finishing touches
  • 📝 Generate Docstrings
🧪 Generate unit tests
  • Create PR with unit tests
  • Post copyable unit tests in a comment
  • Commit unit tests in branch refactor/#314-notification-redirect-data-structure

Tip

👮 Agentic pre-merge checks are now available in preview!

Pro plan users can now enable pre-merge checks in their settings to enforce checklists before merging PRs.

  • Built-in checks – Quickly apply ready-made checks to enforce title conventions, require pull request descriptions that follow templates, validate linked issues for compliance, and more.
  • Custom agentic checks – Define your own rules using CodeRabbit’s advanced agentic capabilities to enforce organization-specific policies and workflows. For example, you can instruct CodeRabbit’s agent to verify that API documentation is updated whenever API schema files are modified in a PR. Note: Upto 5 custom checks are currently allowed during the preview period. Pricing for this feature will be announced in a few weeks.

Please see the documentation for more information.

Example:

reviews:
  pre_merge_checks:
    custom_checks:
      - name: "Undocumented Breaking Changes"
        mode: "warning"
        instructions: |
          Pass/fail criteria: All breaking changes to public APIs, CLI flags, environment variables, configuration keys, database schemas, or HTTP/GraphQL endpoints must be documented in the "Breaking Change" section of the PR description and in CHANGELOG.md. Exclude purely internal or private changes (e.g., code not exported from package entry points or explicitly marked as internal).

Please share your feedback with us on this Discord post.


Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

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

@github-actions
Copy link

Test Results

479 tests   479 ✅  44s ⏱️
142 suites    0 💤
142 files      0 ❌

Results for commit a9145c7.

Copy link

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

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

Actionable comments posted: 1

🧹 Nitpick comments (6)
src/test/java/konkuk/thip/notification/application/service/RoomNotificationOrchestratorSyncImplTest.java (1)

9-9: PostType 전환은 적절합니다. redirectSpec(openComments)까지 검증 추가 권장

PR 목적(알림 리다이렉트 데이터 구조 검증)을 테스트에서 보장하려면, 저장된 Notification의 redirectSpec이 ROOM_POST_DETAIL 이고 params에 openComments=true 및 postType이 포함되는지까지 검증해 주세요. 현재는 이벤트 발행만 검증하고 있어 결함이 발생해도 놓칠 수 있습니다.

Also applies to: 67-67, 87-87, 114-114, 150-150

src/test/java/konkuk/thip/notification/application/service/RoomNotificationOrchestratorSyncImplUnitTest.java (1)

33-37: redirectSpec 캡처하여 route 및 openComments=true 검증 추가 제안

유닛 테스트에서 NotificationRedirectSpec을 ArgumentCaptor로 캡처하면 ROOM_POST_DETAIL 및 openComments=true/postType=RECORD를 확실히 보장할 수 있습니다.

적용 예시(diff):

@@
-        // when
-        sut.notifyRoomPostCommented(targetUserId, actorUserId, actorUsername, roomId, page, postId, postType);
+        // when
+        sut.notifyRoomPostCommented(targetUserId, actorUserId, actorUsername, roomId, page, postId, postType);
@@
-        ArgumentCaptor<EventCommandInvoker> invokerCaptor = ArgumentCaptor.forClass(EventCommandInvoker.class);
-        verify(notificationSyncExecutor).execute(
-                any(),                // template
-                any(),                // args
-                eq(targetUserId),     // targetUserId
-                any(),                // redirectSpec
-                invokerCaptor.capture() // invoker
-        );
+        ArgumentCaptor<NotificationRedirectSpec> redirectCaptor = ArgumentCaptor.forClass(NotificationRedirectSpec.class);
+        ArgumentCaptor<EventCommandInvoker> invokerCaptor = ArgumentCaptor.forClass(EventCommandInvoker.class);
+        verify(notificationSyncExecutor).execute(
+                any(),                 // template
+                any(),                 // args
+                eq(targetUserId),      // targetUserId
+                redirectCaptor.capture(), // redirectSpec
+                invokerCaptor.capture()   // invoker
+        );
@@
-        // then: invoker 가 EventCommandPort 메서드를 올바르게 호출하는지 검증
+        // then: redirectSpec 검증
+        NotificationRedirectSpec redirect = redirectCaptor.getValue();
+        assertThat(redirect.route()).isEqualTo(MessageRoute.ROOM_POST_DETAIL);
+        assertThat(redirect.params()).containsEntry("openComments", true)
+                                     .containsEntry("postType", PostType.RECORD)
+                                     .containsEntry("roomId", roomId)
+                                     .containsEntry("page", page)
+                                     .containsEntry("postId", postId);
+
+        // then: invoker 가 EventCommandPort 메서드를 올바르게 호출하는지 검증
         EventCommandInvoker invoker = invokerCaptor.getValue();

파일 상단 import 추가:

import konkuk.thip.notification.domain.value.MessageRoute;
import konkuk.thip.notification.domain.value.NotificationRedirectSpec;

Also applies to: 39-46, 49-54

src/main/java/konkuk/thip/comment/application/service/CommentLikeService.java (1)

74-87: switch 분기 내 일관성 유지 및 신규 enum 대비 기본 분기 추가 권장

  • getPostQueryDto 호출 시 이미 로컬 변수로 꺼낸 postType을 재사용해 일관성과 가독성을 높이세요.
  • 향후 PostType이 추가될 경우 대비해 default 분기에서 예외를 던져 누락된 케이스를 조기에 발견할 수 있게 하세요.

제안 diff:

-        PostType postType = comment.getPostType();
+        PostType postType = comment.getPostType();
@@
-            case RECORD, VOTE -> {
-                    PostQueryDto postQueryDto = postHandler.getPostQueryDto(comment.getPostType(), comment.getTargetPostId());
+            case RECORD, VOTE -> {
+                    PostQueryDto postQueryDto = postHandler.getPostQueryDto(postType, comment.getTargetPostId());
                     roomNotificationOrchestrator.notifyRoomCommentLiked(
                             comment.getCreatorId(), actorUser.getId(), actorUser.getNickname(), postQueryDto.roomId(), postQueryDto.page(), postQueryDto.postId(), postType
                     );
             }
+            default -> throw new IllegalStateException("Unsupported postType: " + postType);
src/main/java/konkuk/thip/comment/application/service/CommentCreateService.java (2)

96-107: 신규 PostType 추가 대비 기본 분기(default)에서 예외 처리 권장

switch가 FEED/RECORD/VOTE만 다루므로 후속 enum 추가 시 테스트 없이 누락될 수 있습니다. default에서 예외를 던져 결함을 빠르게 감지하세요.

         switch (postType) {
             case FEED ->    // 피드 댓글 알림 이벤트 발행
                     feedNotificationOrchestrator.notifyFeedCommented(
                             postQueryDto.creatorId(), actorUser.getId(), actorUser.getNickname(), postQueryDto.postId()
                     );
             case RECORD, VOTE ->    // 모임방 게시글 댓글 알림 이벤트 발행
                     roomNotificationOrchestrator.notifyRoomPostCommented(
                             postQueryDto.creatorId(), actorUser.getId(), actorUser.getNickname(),
                             postQueryDto.roomId(), postQueryDto.page(), postQueryDto.postId(), postType
                     );
+            default -> throw new IllegalStateException("Unsupported postType: " + postType);
         }

113-124: 답글 알림 분기에도 기본 분기(default) 추가 권장

동일한 이유로 reply 알림 switch에도 default 예외를 추가해 주세요.

         switch (postType) {
             case FEED ->    // 피드 답글 알림 이벤트 발행
                     feedNotificationOrchestrator.notifyFeedReplied(
                             parentCommentDto.creatorId(), actorUser.getId(), actorUser.getNickname(), postQueryDto.postId()
                     );
             case RECORD, VOTE ->    // 모임방 게시글 답글 알림 이벤트 발행
                     roomNotificationOrchestrator.notifyRoomPostCommentReplied(
                             parentCommentDto.creatorId(), actorUser.getId(), actorUser.getNickname(),
                             postQueryDto.roomId(), postQueryDto.page(), postQueryDto.postId(), postType
                     );
+            default -> throw new IllegalStateException("Unsupported postType: " + postType);
         }
src/main/java/konkuk/thip/notification/application/service/RoomNotificationOrchestratorSyncImpl.java (1)

207-231: Map.of null 불가 특성 대비 선제적 널 가드 추가 권장

Map.of은 null key/value를 허용하지 않습니다. page 등이 null일 가능성이 있다면 런타임 NPE가 납니다. 사전 검증으로 실패 지점을 명확히 해 주세요.

diff(두 헬퍼 모두 적용):

     private NotificationRedirectSpec createRoomPostWithCommentsRedirectSpec(Long roomId, Integer page, Long postId, PostType postType) {
+        java.util.Objects.requireNonNull(roomId, "roomId must not be null");
+        java.util.Objects.requireNonNull(page, "page must not be null");
+        java.util.Objects.requireNonNull(postId, "postId must not be null");
+        java.util.Objects.requireNonNull(postType, "postType must not be null");
         return new NotificationRedirectSpec(
                 MessageRoute.ROOM_POST_DETAIL,
                 Map.of(
                         "roomId", roomId,
                         "page", page,
                         "postId", postId,
                         "postType", postType,
                         "openComments", true
                 )
         );
     }
@@
     private NotificationRedirectSpec createRoomPostRedirectSpec(Long roomId, Integer page, Long postId, PostType postType) {
+        java.util.Objects.requireNonNull(roomId, "roomId must not be null");
+        java.util.Objects.requireNonNull(page, "page must not be null");
+        java.util.Objects.requireNonNull(postId, "postId must not be null");
+        java.util.Objects.requireNonNull(postType, "postType must not be null");
         return new NotificationRedirectSpec(
                 MessageRoute.ROOM_POST_DETAIL,
                 Map.of(
                         "roomId", roomId,
                         "page", page,
                         "postId", postId,
                         "postType", postType,
                         "openComments", false
                 )
         );
     }

가능하면 상단에 import 추가:

import java.util.Objects; // 사용 시 java.util.Objects. 접두어 제거
📜 Review details

Configuration used: CodeRabbit UI

Review profile: CHILL

Plan: Pro

Disabled knowledge base sources:

  • Jira integration is disabled by default for public repositories

You can enable these sources in your CodeRabbit configuration.

📥 Commits

Reviewing files that changed from the base of the PR and between 0913cfb and a9145c7.

📒 Files selected for processing (10)
  • src/main/java/konkuk/thip/comment/application/service/CommentCreateService.java (1 hunks)
  • src/main/java/konkuk/thip/comment/application/service/CommentLikeService.java (1 hunks)
  • src/main/java/konkuk/thip/notification/application/port/in/RoomNotificationOrchestrator.java (3 hunks)
  • src/main/java/konkuk/thip/notification/application/service/RoomNotificationOrchestratorSyncImpl.java (8 hunks)
  • src/main/java/konkuk/thip/notification/domain/value/MessageRoute.java (1 hunks)
  • src/main/java/konkuk/thip/post/adapter/out/persistence/PostLikeCommandPersistenceAdapter.java (0 hunks)
  • src/main/java/konkuk/thip/post/application/service/PostLikeService.java (1 hunks)
  • src/main/java/konkuk/thip/roompost/application/service/RoomPostSearchService.java (1 hunks)
  • src/test/java/konkuk/thip/notification/application/service/RoomNotificationOrchestratorSyncImplTest.java (5 hunks)
  • src/test/java/konkuk/thip/notification/application/service/RoomNotificationOrchestratorSyncImplUnitTest.java (2 hunks)
💤 Files with no reviewable changes (1)
  • src/main/java/konkuk/thip/post/adapter/out/persistence/PostLikeCommandPersistenceAdapter.java
🧰 Additional context used
🧠 Learnings (1)
📓 Common learnings
Learnt from: seongjunnoh
PR: THIP-TextHip/THIP-Server#113
File: src/main/java/konkuk/thip/recentSearch/adapter/out/persistence/RecentSearchCommandPersistenceAdapter.java:38-44
Timestamp: 2025-07-30T14:05:04.945Z
Learning: seongjunnoh는 코드 최적화 제안에 대해 구체적인 기술적 근거와 효율성 차이를 이해하고 싶어하며, 성능 개선 방식에 대한 상세한 설명을 선호한다.
Learnt from: seongjunnoh
PR: THIP-TextHip/THIP-Server#93
File: src/main/java/konkuk/thip/room/adapter/out/persistence/RoomQueryPersistenceAdapter.java:49-114
Timestamp: 2025-07-28T16:44:31.224Z
Learning: seongjunnoh는 코드 중복 문제에 대한 리팩토링 제안을 적극적으로 수용하고 함수형 인터페이스를 활용한 해결책을 선호한다.
Learnt from: seongjunnoh
PR: THIP-TextHip/THIP-Server#285
File: src/main/java/konkuk/thip/room/adapter/out/jpa/RoomStatus.java:1-7
Timestamp: 2025-08-31T05:25:14.845Z
Learning: seongjunnoh는 enum 의존성에 대해 유연한 접근을 선호하며, 도메인→어댑터 레이어 참조와 같은 아키텍처 layering 원칙보다 실용적인 구현을 우선시한다.
Learnt from: seongjunnoh
PR: THIP-TextHip/THIP-Server#195
File: src/main/java/konkuk/thip/feed/application/mapper/FeedQueryMapper.java:0-0
Timestamp: 2025-08-13T05:22:32.287Z
Learning: seongjunnoh는 데이터 무결성과 중복 방지에 대한 고민이 깊으며, LinkedHashSet을 활용한 중복 제거와 순서 보장을 동시에 달성하는 솔루션을 선호한다.
Learnt from: seongjunnoh
PR: THIP-TextHip/THIP-Server#305
File: src/main/java/konkuk/thip/notification/adapter/out/persistence/repository/NotificationQueryRepository.java:9-13
Timestamp: 2025-09-17T06:40:49.863Z
Learning: seongjunnoh는 메서드 네이밍 시 구현 세부사항보다 비즈니스 의도를 반영하는 것을 선호하며, 미래 확장성과 아키텍처 변화를 고려한 설계 철학을 가지고 있다.
Learnt from: seongjunnoh
PR: THIP-TextHip/THIP-Server#278
File: src/main/java/konkuk/thip/TestTokenController.java:0-0
Timestamp: 2025-08-24T09:33:52.982Z
Learning: seongjunnoh는 Spring의 ConditionalOnProperty 동작 원리를 정확히 이해하고 있으며, 보안 이슈에 대해서도 실질적인 위험성을 기준으로 판단하는 실용적 접근을 선호한다.
Learnt from: seongjunnoh
PR: THIP-TextHip/THIP-Server#278
File: src/main/java/konkuk/thip/common/exception/code/ErrorCode.java:210-211
Timestamp: 2025-08-24T09:40:48.595Z
Learning: seongjunnoh는 HTTP 상태 코드 선택에 대해 기술적 근거와 코드베이스 내 일관성을 중요하게 생각하며, 구체적인 사례 분석을 통한 설명을 선호한다.
Learnt from: seongjunnoh
PR: THIP-TextHip/THIP-Server#180
File: src/main/java/konkuk/thip/room/application/service/AttendanceCheckCreateService.java:22-40
Timestamp: 2025-08-14T09:15:31.371Z
Learning: seongjunnoh는 기술적 완벽성보다 실제 비즈니스 시나리오와 사용자 행동 패턴을 우선 고려하며, 발생 가능성이 낮은 엣지 케이스보다는 실용적인 구현을 선호한다.
Learnt from: seongjunnoh
PR: THIP-TextHip/THIP-Server#112
File: src/main/java/konkuk/thip/feed/adapter/out/persistence/repository/FeedQueryRepositoryImpl.java:272-272
Timestamp: 2025-07-30T10:44:34.115Z
Learning: seongjunnoh는 피드 커서 페이지네이션에서 LocalDateTime 단일 커서 방식을 선호하며, 복합 키 기반 커서보다 구현 단순성과 성능을 우선시한다.
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (1)
  • GitHub Check: build
🔇 Additional comments (9)
src/main/java/konkuk/thip/roompost/application/service/RoomPostSearchService.java (1)

51-51: 기본 페이지 사이즈 20 상향, 비즈니스 요구에 부합합니다
Cursor.from(...)에 전달되는 기본 사이즈가 20으로 바뀌면서 프론트에서 요청한 “한 번에 더 많은 게시물 로딩” 요구사항을 충족할 수 있을 듯합니다. voteQueryPort.findVoteItemsByVoteIdspostLikeQueryPort.findPostIdsLikedByUser도 ID 집합 크기가 20개 이하라면 인메모리/IN 절 부담이 크지 않아 보입니다. 👍

src/main/java/konkuk/thip/post/application/service/PostLikeService.java (1)

75-83: PostType 기반 분기 전환 굿
기존 문자열 비교보다 컴파일 타임 체크가 가능해져 유지보수성이 확실히 올라간 것 같습니다.

src/main/java/konkuk/thip/notification/application/service/RoomNotificationOrchestratorSyncImpl.java (6)

34-48: 댓글 알림에 openComments=true 적용 LGTM

리다이렉트 스펙 헬퍼 적용으로 의도 명확하고 중복 제거되었습니다.


52-66: 투표 시작 알림: openComments=false, PostType.VOTE 고정 LGTM


70-85: 기록 생성 알림: openComments=false, PostType.RECORD 고정 LGTM


153-167: 댓글 좋아요 알림에 openComments=true 적용 LGTM


171-186: 게시글 좋아요 알림에 openComments=false 적용 LGTM


190-205: 답글 알림에 openComments=true 적용 LGTM

src/main/java/konkuk/thip/notification/application/port/in/RoomNotificationOrchestrator.java (1)

3-3: 구현/호출부 전역 정합성 확인
rg 스크립트 실행 결과, String 기반 시그니처/호출 사례가 없습니다. 마지막으로 수동 검토 바랍니다.

ROOM_POST_DETAIL, // 특정 모임 게시글 상세 화면으로 이동 -> PostType으로 투표인지 기록인지 판단
ROOM_RECORD_DETAIL, // 특정 모임 기록 상세 화면으로 이동 (기록장 조회 - 페이지 필터 걸린채로)
ROOM_VOTE_DETAIL; // 특정 모임 투표 상세 화면으로 이동 (투표 조회 - 페이지 필터 걸린채로)
ROOM_POST_DETAIL, // 특정 모임 게시글 상세 화면으로 이동 -> PostType으로 투표(VOTE)인지 기록(RECORD)인지 판단
Copy link

@coderabbitai coderabbitai bot Sep 25, 2025

Choose a reason for hiding this comment

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

⚠️ Potential issue

기존 알림 레코드 역직렬화가 실패합니다.

현재 DB/캐시에는 ROOM_RECORD_DETAIL, ROOM_VOTE_DETAIL 값으로 저장된 알림이 이미 존재합니다. 이 enum 상수를 제거하면 Enum.valueOf/JPA 매핑 과정에서 IllegalArgumentException이 발생하여 알림 조회 자체가 실패합니다. 배포 전에 데이터 마이그레이션이 보장되지 않는다면, 최소한 레거시 상수를 남겨두고 내부 로직에서 ROOM_POST_DETAIL로 매핑하는 완충 장치가 필요합니다.

예시 수정안:

     ROOM_DETAIL,            // 특정 모임 상세정보 화면으로 이동
-    ROOM_POST_DETAIL,       // 특정 모임 게시글 상세 화면으로 이동 -> PostType으로 투표(VOTE)인지 기록(RECORD)인지 판단
+    @Deprecated
+    ROOM_RECORD_DETAIL,     // Legacy: PostType.RECORD로 해석
+    @Deprecated
+    ROOM_VOTE_DETAIL,       // Legacy: PostType.VOTE로 해석
+    ROOM_POST_DETAIL,       // 특정 모임 게시글 상세 화면으로 이동 -> PostType으로 투표(VOTE)인지 기록(RECORD)인지 판단

레거시 값을 허용하되, 새 알림 생성 시에는 ROOM_POST_DETAIL만 사용하도록 다른 계층에서 제한하는 방식으로 전환해 주세요.

🤖 Prompt for AI Agents
In src/main/java/konkuk/thip/notification/domain/value/MessageRoute.java around
line 19, removing legacy enum constants (ROOM_RECORD_DETAIL, ROOM_VOTE_DETAIL)
causes Enum.valueOf/JPA deserialization failures for existing DB/cache records;
restore those legacy constants in the enum (marking them as deprecated if
desired) and implement a mapping layer in the enum (or a helper method) that
maps legacy constants to the new canonical value ROOM_POST_DETAIL for runtime
logic, while ensuring any new notifications are created using only
ROOM_POST_DETAIL at higher layers.

Copy link
Collaborator Author

Choose a reason for hiding this comment

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

아직 알림 부분은 개발 단계여서 기존 데이터를 전부 삭제하는 것으로 정했어!

Copy link

Choose a reason for hiding this comment

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

@seongjunnoh 명확한 설명 감사합니다!

알림 기능이 아직 개발 단계이고 기존 데이터를 모두 삭제할 계획이라면, ROOM_RECORD_DETAILROOM_VOTE_DETAIL enum 상수 제거에 따른 역직렬화 문제는 발생하지 않겠네요. 깔끔한 데이터 구조로 새롭게 시작하는 것이 개발 단계에서는 적절한 접근 방식입니다.

이 경우 현재의 리팩토링이 안전하게 진행될 수 있습니다. 🎉


✏ Learnings added
Learnt from: seongjunnoh
PR: THIP-TextHip/THIP-Server#315
File: src/main/java/konkuk/thip/notification/domain/value/MessageRoute.java:19-19
Timestamp: 2025-09-25T02:39:46.795Z
Learning: seongjunnoh는 아직 개발 단계인 기능에 대해서는 기존 데이터를 삭제하고 새롭게 시작하는 방식을 선호하며, 이를 통해 breaking change 없이 깔끔한 리팩토링을 진행한다.

Note: Learnings are effective only in the context of similar code segments. To apply general coding guidelines, please configure review instructions. You can manage existing learnings in the app.


🧠 Learnings used
Learnt from: seongjunnoh
PR: THIP-TextHip/THIP-Server#113
File: src/main/java/konkuk/thip/recentSearch/adapter/out/persistence/RecentSearchCommandPersistenceAdapter.java:38-44
Timestamp: 2025-07-30T14:05:04.945Z
Learning: seongjunnoh는 코드 최적화 제안에 대해 구체적인 기술적 근거와 효율성 차이를 이해하고 싶어하며, 성능 개선 방식에 대한 상세한 설명을 선호한다.

Learnt from: seongjunnoh
PR: THIP-TextHip/THIP-Server#93
File: src/main/java/konkuk/thip/room/adapter/out/persistence/RoomQueryPersistenceAdapter.java:49-114
Timestamp: 2025-07-28T16:44:31.224Z
Learning: seongjunnoh는 코드 중복 문제에 대한 리팩토링 제안을 적극적으로 수용하고 함수형 인터페이스를 활용한 해결책을 선호한다.

Learnt from: seongjunnoh
PR: THIP-TextHip/THIP-Server#285
File: src/main/java/konkuk/thip/room/adapter/out/jpa/RoomStatus.java:1-7
Timestamp: 2025-08-31T05:25:14.845Z
Learning: seongjunnoh는 enum 의존성에 대해 유연한 접근을 선호하며, 도메인→어댑터 레이어 참조와 같은 아키텍처 layering 원칙보다 실용적인 구현을 우선시한다.

Learnt from: seongjunnoh
PR: THIP-TextHip/THIP-Server#195
File: src/main/java/konkuk/thip/feed/application/mapper/FeedQueryMapper.java:0-0
Timestamp: 2025-08-13T05:22:32.287Z
Learning: seongjunnoh는 데이터 무결성과 중복 방지에 대한 고민이 깊으며, LinkedHashSet을 활용한 중복 제거와 순서 보장을 동시에 달성하는 솔루션을 선호한다.

Learnt from: seongjunnoh
PR: THIP-TextHip/THIP-Server#305
File: src/main/java/konkuk/thip/notification/adapter/out/persistence/repository/NotificationQueryRepository.java:9-13
Timestamp: 2025-09-17T06:40:49.863Z
Learning: seongjunnoh는 메서드 네이밍 시 구현 세부사항보다 비즈니스 의도를 반영하는 것을 선호하며, 미래 확장성과 아키텍처 변화를 고려한 설계 철학을 가지고 있다.

Learnt from: seongjunnoh
PR: THIP-TextHip/THIP-Server#278
File: src/main/java/konkuk/thip/TestTokenController.java:0-0
Timestamp: 2025-08-24T09:33:52.982Z
Learning: seongjunnoh는 Spring의 ConditionalOnProperty 동작 원리를 정확히 이해하고 있으며, 보안 이슈에 대해서도 실질적인 위험성을 기준으로 판단하는 실용적 접근을 선호한다.

Learnt from: seongjunnoh
PR: THIP-TextHip/THIP-Server#278
File: src/main/java/konkuk/thip/common/exception/code/ErrorCode.java:210-211
Timestamp: 2025-08-24T09:40:48.595Z
Learning: seongjunnoh는 HTTP 상태 코드 선택에 대해 기술적 근거와 코드베이스 내 일관성을 중요하게 생각하며, 구체적인 사례 분석을 통한 설명을 선호한다.

Learnt from: seongjunnoh
PR: THIP-TextHip/THIP-Server#180
File: src/main/java/konkuk/thip/room/application/service/AttendanceCheckCreateService.java:22-40
Timestamp: 2025-08-14T09:15:31.371Z
Learning: seongjunnoh는 기술적 완벽성보다 실제 비즈니스 시나리오와 사용자 행동 패턴을 우선 고려하며, 발생 가능성이 낮은 엣지 케이스보다는 실용적인 구현을 선호한다.

Learnt from: seongjunnoh
PR: THIP-TextHip/THIP-Server#112
File: src/main/java/konkuk/thip/feed/adapter/out/persistence/repository/FeedQueryRepositoryImpl.java:272-272
Timestamp: 2025-07-30T10:44:34.115Z
Learning: seongjunnoh는 피드 커서 페이지네이션에서 LocalDateTime 단일 커서 방식을 선호하며, 복합 키 기반 커서보다 구현 단순성과 성능을 우선시한다.

@seongjunnoh seongjunnoh merged commit b3f59af into develop Sep 25, 2025
4 checks passed
@seongjunnoh seongjunnoh deleted the refactor/#314-notification-redirect-data-structure branch September 25, 2025 02:40
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

[THIP2025-359] [refactor] 알림 리다이렉트를 위한 data 구성 수정

2 participants