[Westagram] : 댓글/대댓글 등록

Kiyong Lee·2021년 10월 3일
0

Django

목록 보기
22/35
post-custom-banner

과제

대댓글은 제일 마지막 미션인데, 코드를 분리하기 귀찮아서 한 번에 함

대댓글은 댓글도 만들어봤으니 한 번 만들어봐라.. 라는 과제


코드


models.py

from django.db    import models
from django.db.models.deletion import SET_NULL

from users.models import TimeStampedModel


# Create your models here.
class Comment(TimeStampedModel) :
    email   = models.ForeignKey('users.User' ,on_delete=models.CASCADE)
    posting = models.ForeignKey('postings.Posting', on_delete=models.CASCADE)
    reply   = models.CharField(max_length=100)
    parent_comment = models.ForeignKey('self', on_delete=SET_NULL, null=True)

    class Meta :

        db_table = 'comments'

일반적으로 댓글을 등록할 때 한글자라도 입력해야 하기 때문에 null=True는 주지 않았고
스페이스바만 입력해서 빈칸으로 입력하는거도 내 기억에는 그런것도 허용해주는
웹사이트는 없던거 같아서 blank=True도 설정하지 않았음

원래 댓글의 필드명은 comment였는데, makemigrations 할 때 이름 바꾸라는
경고가 친절하게 떠서 급하게 reply로 수정

parent_comment는 대댓글을 쓸 때 가장 최초의 원댓글의 id를 받아오기 위한 변수
이 필드에 값이 있으면 대댓글이고, 없으면 일반 댓글

on_delete=SET_NULL로 설정한 건, 원 댓글이 삭제됐다고 해서
이전의 대댓글이 날라가는 것이 아니기 때문에 CASCADE 설정 안함


views.py

class CommentsPostView(View) :
    @login_decorator
    def post(self, request) :
        
        try :
            data = json.loads(request.body)

            posting_id = data['posting_id']
            parent_comment_id = data.get('parent_comment_id', None)
            
            if not Posting.objects.filter(id=posting_id).exists() :
                return JsonResponse({'message':'존재하지 않는 게시물입니다.'}, status=400)

            if not Comment.objects.filter(id=parent_comment_id).exists() :
                return JsonResponse({'message':'존재하지 않는 댓글입니다.'}, status=400)


            Comment(
                email_id   = data['email_id'],
                posting_id = posting_id,
                reply      = data['reply'],
                parent_comment_id = parent_comment_id
            ).save()

            return JsonResponse({'message':'댓글 등록 성공'}, status=200)
            
        except KeyError :
            return JsonResponse({'message':'KEY_ERROR'}, status=400)
        
        except json.decoder.JSONDecodeError :
            return JsonResponse({'message':'값을 제대로 입력했는지 확인해보세요'}, status=400)

        except ValueError :
            return JsonResponse({'message':'값 반환이 제대로 안됐네'}, status=400)

원댓글의 유무를 확인하기 위해 data.get()을 써서 있으면 가져오고, 없으면 NULL

내가 댓글쓰는 도중 포스팅한 사람이 삭제할 수 있기 때문에,
포스팅이 존재하는지 조건문을 달아줌(댓글도 마찬가지)

모든 조건에 이상이 없다면 저장 ㄱㄱ

class CommentsGetView(View) :
    @login_decorator
    def get(self, request, id) :

        try :
            #id는 post의 id
            postings = Posting.objects.get(id=id)
            
            comments = postings.comment_set.all()

            result = []

            for comment in comments :

                user = User.objects.get(id=comment.email_id).email

                result.append({
                    "작성자" : user ,
                    "댓글" : comment.comment
                })
            
            return JsonResponse({'comments':result}, status=200)
        
        except TypeError as msg :
            return JsonResponse({'message':msg}, stauts=400)

댓글의 경우, 특정 게시물로 들어가서 확인 가능하므로 포스팅 번호를 가져와야 함
그리고 포스팅의 내용을 통해 댓글에 대해 역참조

profile
ISTJ인 K-개발자
post-custom-banner

0개의 댓글