Returns and Renders

이제 진짜 database에서 비디오를 검색할수 있게 되었다.

전 파트에서 async,awaitcallback의 차이를 배웠다.

아직 callback의 작동 원리가 헷갈릴 수도 있다.

javascriptreturn에 대해 조금만 알아도 return 부분에서 아무 기능을 하지 않는다는 걸 볼 수 있을 거다.

이해 될수 있게 한번 코드를 바꿔 보겠다.

export const home = async (req, res) => {
  Video.find({}, (error, videos) => {
  res.render("home", { pageTitle: "Home", videos });
  });
};

callback 방식의 코드를 복붙 해준거다. return은 아무 기능이 없으니 지워준다.

return이 당장 작동하지 않는 이유는 function안에 있어서다.

그렇기에 function안에서 return은 그저 function을 마무리 할뿐이다.

home에서 return 되는건 어디에도 없다.

export const watch = (req, res) => {
  const { id } = req.params;
  return res.render("watch", { pageTitle: `Watching` });
};

하지만 watch functionretunr하고 있다.

export const home = async (req, res) => {
  Video.find({}, (error, videos) => {
  res.render("home", { pageTitle: "Home", videos });
  });
};

이처럼 또 다른 function 안에 return을 넣으면 home function에서는

return이 없는 것이다.

이걸 이해하는게 중요하다. 이걸 이해하면 express의 작동원리를 조금 알 수 있게 된다.

사실 return 여부는 크게 중요 하지 않다.

중요한건 어떤 function을 호출 했는가 이다.

이제 이 상태에서 페이지를 새로고침하면 아직 모든게 작동하는 걸 볼 수 있다.

render작업이 정상 작동 되고 있다. 이게 되는 이유는 return이 중요한 것이 아니라

render function을 불렀기 때문이다. 그리고 중요한게 하나 더 있다면

res.render 한 번 더 호출 하면 안된다는 거다.

res.render를 중복 실행시 생기는 문제를 보도록 한다.

export const home = async (req, res) => {
  Video.find({}, (error, videos) => {
    console.log("render once");
    res.render("home", { pageTitle: "Home", videos });
    console.log("render again");
    res.render("home", { pageTitle: "Home", videos });
  });
};

다시 말하지만 return이 없어서 이 코드들은 다 실행이 될거다.

하지만 express는 오류를 하나 띄워 줄거다.

새로고침하면 페이지상 오류가 없지만 터미널로 가보면

render once
render again
GET / 304 166.559 ms - -
Error: Cannot set headers after they are sent to the client

render oncerender again은 출력되고 render부분도 이어서 return되지만

client로 전송이 이루어진 뒤 header를 추가 할수 없다고 뜬다.

이 말은 이미 render 한 것은 다시 render 할 수 없음을 말한다.

다른 예시를 보겠다.

export const home = async (req, res) => {
  Video.find({}, (error, videos) => {
    console.log("render once");
    res.render("home", { pageTitle: "Home", videos });
    console.log("render again");
    res.sendStatus(200);
  });
};

지금 render 한 후 sendStatus를 썼다.

새로고침 하면 출력 화면에는 이상이 없지만 에러를 보면 전에 봤던 에러와 같은 에러를 확인 할수 있다.

지금 쯤이면 무엇을 return하는 것이 중요 한게 아니라 어떤 functrion을 호출하는 지가 더 중요하다는 것을 깨달았을거다.

이 같은 경우 render function으로 render 기능을 실행했다.

그럼에도 return을 써주는 이유는 functionrender 작업 후에 종료 되도록 하기 위해서다.

그렇기 때문에 return자체는 필수 요소는 아니다.

export const home = async (req, res) => {
  Video.find({}, (error, videos) => {
    console.log("render once");
    return res.render("home", { pageTitle: "Home", videos });
    console.log("render again");
    res.sendStatus(200);
  });
};

이렇게 return을 적어주니깐 Visual Studio가 그 아래 코드는 실행 안 됨으로 표시를 해준다. (불투명 처리가 된다.)

이 (불투명) 코드는 절대 실행 되지 않는다.

접근 할수 없는 코드입니다. 라고 설명이 나온다. 이게 다 returnfunction을 종료시키기 때문이다.

계속 강조 하지만 return이 아니라 실행되는 function들에 집중 해야된다.

예를 들어 redirect뒤에 render를 할수 없다.

return이 아무것도 안 하는데 왜 존재하는지에 대해 답해 주는 거다.

return은 해당 function을 종료 시켜 주는 기능을 한다.

물론 이런 return을 한다면

export const home = async (req, res) => {
  Video.find({}, (error, videos) => {
    console.log("render once");
    return res.render("home", { pageTitle: "Home", videos });
  });
  return res.end();
};
    return res.render("home", { pageTitle: "Home", videos });

이건 작동 하지 않게 된다. 새로고침을 해보면 페이지에 아무것도 뜨지 않게 된다.

서버 연글을 끊었기 때문이다. 그로 인해 homerender되지 않는다.

이 현상도 callback 방식을 따르기에 생기는 현상이다.

여기서 res.endres.render보다 빨리 실행 된거다.

그리고 터미널에서도 에러가 발생 한걸 확인 할수 있는데 이건 서버 연결을 끊고 render를 시도해서

생긴 에러이다.

return은 필수가 아니고 필요한 function만 불러주면 된다.

그럼 코드를 설명 전 으로 돌려 놓도록 한다.

export const home = async (req, res) => {
  const videos = await Video.find({});
  return res.render("home", { pageTitle: "Home", videos });
};

모든 비디오를 database에서 불러 오는 거다.

현재 검색 조건 없다. 검색 기능은 나중에 만들거다.

다음으로 넘어가기전에 template을 약간 수정해 준다.

home.pug로 가서

extends base
include mixins/video

block content 
    each view in videos 
        +video(view)
    else    
        div Sorry nothing found.

이렇게 해준다.

다음으로 upload video를 배워 보겠다.

upload video는 진짜 비디오를 볼수 잇께 만들어 줄거다.

추가적으로 databaseobject를 생성하는 법도 배울거다.

그리고 Mongo console이 계속 show databases 중이면 wetubedatabase

여기에 존재 하지 않는다.

이건 이곳에 첫 문서를 만들면 해결이 될거다. 다음 파트에서 배워 보도록 한다.

이번 파트에선 return이 아니라 render가 중요한 걸 기억하자.

하지만 returnrender옆에 써서 render이후 작동 되는 function이 없게 했다.

실수를 줄이기 위함이다.

return 없는 코드로 render해도 이상은 없다.

새로고침해도 return이 있을 때와 없을때의 차이가 없다.

중요한건 사람은 누구나 실수를 하는데 render뒤에 redirect를 불러 놓고 왜 문제인지

모를때가 있다.

function중 하나만 불러 올수 있는 걸 명심하고 그리고 return 을 적어서 실수를 방지하는 것이 좋다.

좋은 웹페이지 즐겨찾기