Node.js/Express Pug(view engine)-2
05 May 2021Pug
에서는 파일 내부 구조를 효과적으로 나누고 합칠 수 있도록 다양한 키워드들을 제공해 준다.
views를 만들다 보면 head
나 footer
등과 같은 layout, 또는 필수 script 등은 모든 파일에 들어가야 하므로 코드가 중복되게 되는데 이를 크게 줄이면서, 각 태그의 기능별로 코드를 쪼개어 views 파일들도 모듈화하는 느낌을 줌으로써 추후 유지보수에도 좋고 가독성도 높일 수 있다.
예시를 위한 디렉토리 구조
├──node_modules
├─┬src
│ ├─┬controllers
│ │ ├──userController.js
│ │ └──videoController.js
│ ├─┬routers
│ │ ├──globalRouter.js
│ │ ├──userRouter.js
│ │ └──videoRouter.js
│ └─┬views <---------------------
│ ├─┬partial
│ │ └──footer.pug
│ ├──base.pug
│ ├──home.pug
│ └──watch.pug
├──server.js
└──pakage.json
☄ Includes
https://pugjs.org/language/includes.html
한 Pug 파일의 내용을 다른 Pug 파일에 삽입할 수 있다.
footer
는 거의 모든 파일에 들어가는 태그이며 내용이다. 따라서 이 코드만 따로 파일로 만들어서 include
하면 중복도 줄이고 수정할 일이 생길 때 footer.pug
만 수정하면 되기 때문에 매우 효율적이다.
// home.pug
doctype html
html(lang="ko")
head
title Wetube
body
h1 Welcome to Wetube
include partials/footer.pug
// watch.pug
doctype html
html(lang="ko")
head
title Wetube
body
h1 Watch video
include partials/footer.pug
// partials/footer.pug
footer © #{new Date().getFullYear()} Wetube
#{}
문법은 .pug
에서 JavaScript 코드를 사용할 수 있게 해준다.
위 코드에서는 현재 년도를 가져와 넣어 준다.
☄ Inheritance: Extends and Block
https://pugjs.org/language/inheritance.html
Pug는
Extends
와Block
키워드로 템플릿 상속을 지원한다.
include
를 사용하더라도 중복되는 코드가 많이 발생하고 include
조차 중복해서 작성해 줘야 된다. 그렇다고 모두 개별적으로 .pug
파일을 만들어 관리하기도 오히려 더 복잡해 지는 느낌이 있다.
이때 사용하면 좋은 키워드가 Extends
와 Block
키워드다. html은 기본적으로 필수 태그들이 존재하고, 개발자가 원하는 base layout이 존재하기 마련이다. 이를 하나의 파일에 작성하고 Extends
키워드를 이용해 다른 파일들에서 가져다 쓸 수 있다.
단, include
와의 차이점은 Extends
의미에서 처럼 단순히 가져다 쓰는 것이 아니라 내부 코드에 Block
키워드를 이용해서 각 파일별로 필요한 코드들을 원하는 위치에 추가하는 식으로 확장할 수 있다.
때문에 다른 .pug
파일을 마치 상속해서 사용하기 때문에 템플릿 상속을 지원한다는 설명이 붙여있다.
// base.pug
doctype html
html(lang="ko")
head
block head
body
block content
include partials/footer.pug
// home.pug
extends base.pug
block head
title home | WeTube
block content
h1 This is home !
// watch.pug
extends base.pug
block head
title watch | WeTube
block content
h1 Watch Video !
☄ Pug 템플릿에서 Variables 사용하기
컨트롤러에서 렌더링 할 .pug
파일에서 사용할 수 있도록 객체(변수)들을 넘겨줄 수 있다.
Response.render(view: string, options?: object, callback?: (err: Error, html: string) => void): void
예를 들어 위 예제에서 title
태그를 보면 타이틀 | WeTube
부분이 중복된다. block head
를 다른 파일에서 지우고 base.pug
에서 템플릿 변수를 이용해 한 번에 처리할 수 있다.
// videoController.js 일부분
export const trending = (req, res) => res.render("home", { pageTitle: "home" });
위와 같이 res.render
의 두 번째 인자에 템플릿에서 사용할 변수를 object로 속성과 값으로 지정해 넘겨 준다.
// base.pug
doctype html
html(lang="ko")
head
head #{pageTitle} | WeTube
body
block content
include partials/footer.pug
// home.pug
extends base.pug
block content
h1 This is home !