[트러블 슈팅] 게임 상세 페이지에서 클릭한 리뷰 강조

2star_·2025년 1월 21일
0

최종 프로젝트

목록 보기
25/32

문제

  • 요구사항: 리뷰 목록에서 특정 리뷰를 클릭했을 때, 게임 상세 페이지에서 해당 리뷰를 눈에 띄게 표시하고 나머지 리뷰와 구분하여 관리하고 싶었습니다.
  • 현상: 기존 API 구조가 이를 지원하지 않았습니다. review_id를 통한 클릭한 리뷰의 강조가 필요하다고 생각했습니다.

해결

  1. API 뷰 수정

    • 기존 뷰를 수정하여 review_id를 쿼리 파라미터로 받아 해당 리뷰를 강조(clicked_review)로 분리하여 동작하고자 설계했습니다.
    • 나머지 리뷰 목록에서 클릭한 리뷰를 제외하여 중복을 방지했습니다.
  2. URL 수정

    • URL 패턴에서 game_id를 쿼리 파라미터로 처리하도록 변경했습니다.
    • 쿼리 형식: /api/game/?game_id={game_id}&review_id={review_id}

기존 코드


class GameDetailAPIView(APIView):
    """
    Game 상세 페이지 API
    """
    permission_classes = [AllowAny]

    def get(self, request, app_id):
        # Game 객체 가져오기
        game = get_object_or_404(Game, appID=app_id)

        # 리뷰 가져오기
        reviews = Review.objects.filter(app_id=app_id)
        my_review = None  # 기본값 설정

        # 사용자가 인증된 경우에만 자신의 리뷰 필터링
        if request.user.is_authenticated:
            my_review = reviews.filter(user_id=request.user.id).first()  # user_id로 매칭
            reviews = reviews.exclude(user_id=request.user.id)

        # 직렬화
        game_serializer = GameSerializer(game)
        my_review_serializer = ReviewSerializer(my_review) if my_review else None
        other_reviews_serializer = ReviewSerializer(reviews, many=True)

        return Response({
            "game": game_serializer.data,
            "my_review": my_review_serializer.data if my_review else None,
            "reviews": other_reviews_serializer.data
        })

수정된 코드

1. API 뷰 (views.py)

class GameDetailAPIView(APIView):
    """
    Game 상세 페이지 API
    """

    permission_classes = [AllowAny]

    def get(self, request):
        # 쿼리 파라미터에서 game_id와 review_id 가져오기
        game_id = request.query_params.get("game_id")
        review_id = request.query_params.get("review_id")

        # game_id가 없을 경우 에러 반환
        if not game_id:
            return Response({"error": "game_id is required."}, status=400)

        # Game 객체 가져오기
        game = get_object_or_404(Game, appID=game_id)

        # 리뷰 가져오기
        reviews = Review.objects.filter(app_id=game_id)
        my_review = None
        clicked_review = None

        # 사용자가 인증된 경우, 자신의 리뷰 필터링
        if request.user.is_authenticated:
            my_review = reviews.filter(user_id=request.user.id).first()
            reviews = reviews.exclude(user_id=request.user.id)

        # review_id가 있는 경우, 해당 리뷰를 clicked_review로 설정
        if review_id:
            try:
                clicked_review = reviews.get(id=review_id)
                reviews = reviews.exclude(id=review_id)
            except Review.DoesNotExist:
                clicked_review = None

        # 직렬화
        game_serializer = GameSerializer(game)
        my_review_serializer = ReviewSerializer(my_review) if my_review else None
        clicked_review_serializer = (
            ReviewSerializer(clicked_review) if clicked_review else None
        )
        other_reviews_serializer = ReviewSerializer(reviews, many=True)

        return Response(
            {
                "game": game_serializer.data,
                "my_review": my_review_serializer.data if my_review else None,
                "clicked_review": clicked_review_serializer.data
                if clicked_review
                else None,
                "reviews": other_reviews_serializer.data,
            }
        )

2. URL 패턴 (urls.py)

path("game/", views.GameDetailAPIView.as_view(), name="game_detail"),

테스트

요청 예시 1: 클릭한 리뷰가 있는 경우

  • URL: /api/game/?game_id=12345&review_id=67890

응답 데이터:

{
    "game": {
        "id": 12345,
        "name": "Game Title",
        "description": "Game description..."
    },
    "my_review": {
        "id": 111,
        "content": "My review content...",
        "rating": 4
    },
    "clicked_review": {
        "id": 67890,
        "content": "This is the clicked review...",
        "rating": 5
    },
    "reviews": [
        {
            "id": 22222,
            "content": "Another review...",
            "rating": 3
        },
        {
            "id": 33333,
            "content": "Yet another review...",
            "rating": 4
        }
    ]
}

요청 예시 2: 클릭한 리뷰가 없는 경우

  • URL: /api/game/?game_id=12345

응답 데이터:

{
    "game": {
        "id": 12345,
        "name": "Game Title",
        "description": "Game description..."
    },
    "my_review": {
        "id": 111,
        "content": "My review content...",
        "rating": 4
    },
    "clicked_review": null,
    "reviews": [
        {
            "id": 67890,
            "content": "Another review...",
            "rating": 5
        },
        {
            "id": 33333,
            "content": "Yet another review...",
            "rating": 4
        }
    ]
}

요약 표

항목설명
문제리뷰 목록에서 게임 상세 페이지로 이동 시 클릭한 리뷰를 눈에 띄게 하고 나머지 리뷰와 분리 필요
해결 방법GameDetailAPIView 수정: review_id를 받아 클릭한 리뷰(clicked_review)를 강조 및 분리
URL 변경/api/game/?game_id={game_id}&review_id={review_id}로 변경
테스트 결과클릭한 리뷰(clicked_review)가 응답에서 별도로 제공되며, 나머지 리뷰(reviews)와 구분됨

API 명세서 링크

profile
안녕하세요.

0개의 댓글

관련 채용 정보