[유튜브 클론코딩] 10.2 API Adding a Comment part.1

2021. 3. 23. 19:58Projects/유튜브 클론코딩

728x90
반응형

10.2 API Adding a Comment part.1

🍎이번시간에 할 것

덧글(Comment) 기능을 구현하기 위해 html과 css는 이미 해놓은 상태이고, 프론트엔드부분을 하기 전에 먼저 백엔드부분을 구현해볼 것이다.

 

Comment를 위한 api 루트 만들기

routes.js에서 루트를 만들어보자. view를 만들었던 것처럼 하면 된다.

const ADD_COMMENT = "/:id/comment";



addComment: ADD_COMMENT //이 부분은 당연히 const routes에 추가

↑ routes.js

 

videoController.js에서 postAddComment함수 만들기

//Add Comment

export const postAddComment = async(req,res) => {

    const {

        params: {id},

        body : {comment}

    } = req;

    try{

        const video = await Video.findById(id);

    }catch(error){

        res.status(400);

    }finally{

        res.end();

    }

}

↑ videoController.js

우리는 정보를 보내고 싶으니까 (데이터베이스를 수정할 것이니까) 이 함수는 POST가 될 것이다.

우린 파라미터로부터 id를 얻을거고, body에서 comment도 얻어 올 것이다.

try-catch-finally로 만들 것이다.

그리고 try에서 비디오를 먼저 얻어 본다. 그래서 비디오가 있는지 없는지 먼저 알아야 하니까.

 

comment를 만들어야 하니까 videoController.js에 models/Comment.js를 import한다.

import Comment from "../models/Comment";

↑ videoController.js

 

// Add Comment

export const postAddComment = async(req,res) => {

    const {

        params: {id},

        body : {comment},

        user

    } = req;

    try{

        const video = await Video.findById(id);

        const newComment = await Comment.create({

            text: comment,

            creator: user.id

        });

        video.comments.push(newComment.id);

        video.save();

    }catch(error){

        res.status(400);

    }finally{

        res.end();

    }

}

그리고  Comment를 create한다. text: comment라는 것은 req.body에서 온 comment를 말하는 것이다.

그리고 현재 로그인한 유저가 req.user라는 객체에 있으므로 user도 비구조화 할당을 했으므로 user.id라고만 치면 된다.

그리고 비디오에 comments라는거 넣어줬던 거 기억하지? 그러니까 video.comments에 newComment의 id를 push하고 video를 저장하면 된다. 이건 마치 비디오를 업로드할 때랑 같았던 것이다.

 

이건 백엔드 파트였고, postAddComment함수는 덧글을 달 때 id는 url에서 가져오고, comment는 body에서 가져온다. video를 찾고, 그리고 newComment를 생성하고 그리고 그 comment id를 video comment에 넣어준다.

 

 

apiRouter로 가서 경로 추가하기

apiRouter.post(routes.addComment, postAddComment);

↑ apiRouter.js

 

여기까지 controlling 파트였다.


이제 하려고 하는 것은 videoDetail.pug로 가서 덧글 리스트를 만들어주는 것이다.

 

videoDetail.pug에서 덧글 리스트를 보여주도록 수정하기

 .video__comments

            if video.comments.length === 1

                span.video__comment-number 1 comment

            else

                span.video__comment-number #{video.comments.length} comments 

            form.add__comment

                    input(type="text", placeholder="Add a comment")

            ul.video__comments-list 

                each comment in video.comments

                    span comment.text 

↑ videoDetail.pug

비디오는 comments를 가지고 있다는 것 기억하지? 우린 그걸 정상적으로 보여줘야 한다.

 

videoController.js > videoDetail 함수로 가서 수정하기

videoDetail 함수에서 전에 Uploaded by 를 하느라 populate를 통해서 creator의 id뿐만 아니라 모든 것을 접근할 수 있었던 것 기억하지? 그것처럼 우리는 comments도 populate해줘야 한다.

// Video Detail

export const videoDetail = async(req, res) => {

    const { params: {id}} = req;

    try{

        const video = await Video.findById(id).populate("creator").populate("comments");

        console.log(video);

        res.render("videoDetail", {pageTitle: video.title, video});

    }catch(error){

        console.log(error);

        res.redirect(routes.home);

    }

};

↑ videoController.js

 

 .video__comments

            if video.comments.length === 1

                span.video__comment-number 1 comment

            else

                span.video__comment-number #{video.comments.length} comments 

            form.add__comment

                    input(type="text", placeholder="Add a comment", name="comment")

            ul.video__comments-list 

                each comment in video.comments

                    span comment.text 

↑ videoDetail.pug

그리고 잊지말고 comment를 작성하는 input에서 name을 comment로 주어야 아까 videoController.js에서 작성했던 postAddComment 함수에서 req.body에서 comment를 받아올 수 있다.

 

 

 

🍏**여기서 이해해야할 것

백엔드는 모든게 동작하는게 같다.

 const {

        params: {id},

        body : {comment},

        user

    } = req;

이건 우리가 form을 submit한 것이랑 똑같이 동작해

submit하는 모든거 (upload video, change password, login같은 폼)

그런데 videoDetail.pug는 액션이나 메소드가 없다. 왜냐하면 우리는 이것을 프론트엔드 부분에서 할 것이기 때문이다.

프론트엔드 부분은 다음시간에 하겠다.

728x90
반응형