Node 學習 -- jade

jade(pug)

因爲商標版權問題,Jade 已經更名爲了 Pug,github地址github.com/pugjs/pugjavascript

Jade 是一個高性能的模板引擎,它是用 JavaScript 實現的,而且能夠供 Node 使用,固然還支持其餘語言。css

文件後綴名爲.pug(.jade)html

jade優勢

  • 可讀性高
  • 靈活的縮進
  • 塊展開
  • 代碼默認通過編碼處理(轉義),安全性高
  • 運行時和編譯時上下文錯誤報告
  • 支持命令行編譯
  • 支持html5模式
  • 在內存中緩存(可選)
  • 原生支持 Express
  • 合併動態和靜態標籤類
  • 過濾器

關於Ejs或者其餘模板引擎與jade比較,能夠看看這篇文章www.zhihu.com/question/20…html5

安裝

npm安裝建議安裝個nrm來進行源管理.java

npm install pug -g
npm install pug-cli -g複製代碼

測試demo

爲了方便編寫代碼,最好把編譯器的tab設置:2.jquery

// index.jade

doctype html
html
  head
    title jade test
  body
    h2 jade study複製代碼
粗暴的編譯方法
pug index.jade

// index.html
<!DOCTYPE html><html><head><title>jade test</title></head><body><h2>jade study </h2></body></html>複製代碼

發現編譯後的代碼不具有可讀性.git

pug -- help
 Options:
     -P, --pretty           compile pretty HTML output ## 輸出漂亮結構的HTML
    -D, --no-debug         compile without debugging (smaller functions) ## 不帶調試的編譯
    -w, --watch            watch files for changes and automatically re-render ## 對某個文件的變更保持監控
    -E, --extension <ext>  specify the output file extension ## 指定輸出文件擴展名
    -s, --silent           do not output logs ## 不輸出日誌複製代碼
// 從新編譯
pug -P index.jade
<!DOCTYPE html>
<html> <head> <title>jade test</title> </head> <body> <h2>jade study </h2> </body> </html>複製代碼
自動編譯

只是爲了學習,這裏只要設置-w -P .開發中經過打包工具來進行自動編譯.github

// 命令行工具推薦使用Cmder

λ pug -P -w index.jade
  watching index.jade
  rendered index.html複製代碼

Express與Pug

Pug徹底集成了一個流行的Node.js Web框架Express,做爲支持的視圖引擎。 看看Express是如何將Pug與Express集成的完美指南。express

在Express中,環境變量NODE_ENV旨在向Web應用程序通知執行環境:不管是在開發中仍是在生產中。 Express和Pug自動修改生產環境中的幾個選項的默認值,爲用戶提供更好的開箱即用體驗。 具體來講,當process.env.NODE_ENV設置爲「production」,Pug與Express一塊兒使用時,compileDebug選項默認爲false,而cache選項爲true。npm

API

標籤屬性
  • id,class寫法
// 編譯前

  p.title class寫法1
  p(class='title') class寫法2
  p#tit id寫法1
  p(id='tit2') id寫法2     

// 編譯後
  <p class="title">class寫法1</p>
  <p class="title">class寫法2</p>
  <p id="tit">id寫法</p>
  <p id="tit2">id寫法2 </p>複製代碼
// 編譯前
- var classArr = ['small','medium','large']
a(class= classArr)
a.test(class = classArr class=['add'])

// 編譯後
<a class="small medium large"></a>
<a class="test small medium large add"></a>複製代碼

它也能夠是將類名映射到true或false值的對象.

//編譯前
- var active = 'select'
a(class={active: active === 'select'} )

// 編譯後
<a class="active"></a>複製代碼
  • 其餘屬性
    經過()來依次編寫屬性,多個用逗號隔開.
//編譯前
a(class='baidu' ,title='baidu' href='www.baidu.com') 百度

//編譯後
<a class="baidu" title="baidu" href="www.baidu.com">百度</a>複製代碼
  • 也支持全部正常的javascript表達式
// 編譯前
- var flag  = true   //注意這裏使用變量要記得添加-符號.
h2(class=flag ? 'flag': '')

// 編譯後
<h2 class="flag"></h2>複製代碼
  • 多個屬性的另外寫法

其實就是換號縮進

// 編譯前
a(
      title='baidu',
      href='www.baidu.com',
      class='links'
)
// 編譯後
<a class="links" title="baidu" href="www.baidu.com"></a>複製代碼

若是您有一個很是長的屬性,而且您的JavaScript運行時支持ES2015模板字符串,則可使用該語法的屬性:

// 編譯前
input(data-json=`
      {
        "very-long": "piece of ",
        "data": true
      }
`)
// 編譯後
<input data-json="
      {
        &quot;very-long&quot;: &quot;piece of &quot;,
        &quot;data&quot;: true
      }
">複製代碼
  • 引用屬性

若是你的屬性名稱包含了與JavaScript語法衝突的字符,請使用""或''引用,或使用逗號分隔不一樣的屬性。

官網舉了個Angular 2的例子.

//(click)='play()',這裏(click)會被看成一個函數調用而不是一個屬性名字來解析.

// 編譯前
div(class='div-class' (click)='play()')

// 編譯後報錯
div(class='div-class' (click)='play()')
---------------------^複製代碼

正確寫法

// 編譯前
div(class='div-class' '(click)'='play()')
div(class='div-class', (click) = 'play()')

// 編譯後
<div class="div-class" (click)="play()"></div>
<div class="div-class" (click)="play()"></div>複製代碼
  • 屬性插值

之前版本的Pug / Jade支持以下插值語法(再也不支持):

//編譯前
- var url = 'www.baidu.com'
a(href='/#{url}') links

//編譯後 已再也不支持
<a href="/#{url}">links</a>複製代碼

新的寫法

// 編譯前
- var url = 'demo.com'
a(href='/' + url) links
- var url2 = 'www.baidu.com'
a(href = url2 ) 百度  

// 編譯後
<a href="/demo.com">links</a>
<a href="www.baidu.com">百度  </a>複製代碼

若是你的javascript運行環境支持ES 2015.那麼Pug支持模板字符串語法

// 編譯前
- var size1 = 'small'
- var size2 = 'medium'
- var size3 = 'large'
button(
  type='button',
  class='btn btn-' + size1 + ' ' +  'btn-' + size2 + ' ' + 'btn-' + size3
)
button(
  type='button',
  class=`btn btn-$(size1) btn-$(size2) btn(size3)`
)
// 編譯後
<button class="btn btn-small btn-medium btn-large" type="button"></button>
<button class="btn btn-small btn-medium btn-large" type="button"></button>複製代碼
  • 未轉義屬性

默認狀況下,會轉義全部屬性(用轉義序列代替特殊字符),以防止諸如跨站點腳本之類的攻擊。 若是必須須要使用特殊字符,可使用!=而不是=。

// 編譯前
div(title="<code>")
div(title!="<code>")

// 編譯後
<div title="&lt;code&gt;"></div>
<div title="<code>"></div>複製代碼
  • 布爾屬性

布爾屬性由Pug鏡像,並接受布爾值(true和false)。 當沒有指定值時,默認爲true。

// 編譯前
input(type='radio' checked)
input(type='radio' checked=true)
input(type='radio' checked=false)

// 編譯後
<input type="radio" checked>
<input type="radio" checked>
<input type="radio">複製代碼
  • style屬性

style屬性能夠是一個字符串(像任何普通屬性),但它也能夠是一個對象

// 編譯前
p(style={fontSize: '14px',color: 'red'})

// 編譯後
<p style="fontSize:14px;color:red;"></p>複製代碼
Case

case語句是JavaScript Switch語句的縮寫,並採用如下形式:

// 編譯前
- var friendsNum = 4
    case friendsNum
      when 0
        p you have not friend
      when 1
        p you has one friend
      default
        p you has #{friendsNum} friends    

// 編譯後
<p>you has 4 friends    </p>複製代碼
// 編譯前
- var friendsNum = 1
    case friendsNum
      when 0
      when 1
        p you has one friend
      default
        p you has #{friendsNum} friends

// 編譯後
<p>you has one friend</p>複製代碼

固然也支持break;

// 編譯前

- var friendsNum = 0
    case friendsNum
      when 0
        - break
      when 1
        p you has one friend
      default
        p you has #{friendsNum} friends

// 編譯後
無內容複製代碼

也可使用塊擴展語法

// 編譯前
  - var friendsNum = 1
    case friendsNum
      when 0
      when 1: p you has one friend
      default: p you has #{friendsNum} friends

// 編譯後
<p>you has one friend</p>複製代碼
Code

Pug能夠在你的模板中編寫內置的JavaScript代碼。 有三種類型的代碼。

  • Unbuffered Code
    不直接添加任何的輸出
// 編譯前
- for(var i = 0; i < 3;i++)
      li item

// 編譯後
<li>item</li>
<li>item</li>
<li>item</li>複製代碼
// 編譯前

- var nameList = ['kobe','cpul','james']
      each item in nameList
        li=item

// 編譯後

<li>kobe</li>
<li>cpul</li>
<li>james</li>複製代碼
  • Buffered Code

以=開頭,並輸出評估模板中JavaScript表達式的結果。 爲了安全起見,首先HTML被轉義:

// 編譯前

p
  = 'this is code template <code>'
p= 'this is code template' + '<code>'  

// 編譯後

<p>this is code template &lt;code&gt;
</p>
<p>this is code template&lt;code&gt;</p>複製代碼
  • Unescaped Buffered Code

未轉義的代碼以!=開頭,並輸出評估模板中JavaScript表達式的結果。 這不會進行任何轉義,因此對用戶輸入是不安全的:

// 編譯前
p
  != 'this is code template <code>'
p!= 'this is code template' + '<code>'  

// 編譯後
<p>this is code template <code>
</p>
<p>this is code template<code></p>複製代碼
Comments註釋
  • 單行註釋
// 編譯前

// 這是一個註釋
p 這是一個註釋

// 編譯後

<!-- 這是一個註釋-->
<p>這是一個註釋</p>複製代碼

Pug還有種註釋寫法,只需添加連字符'-'便可。這些僅用於對Pug代碼自己進行註釋,編譯後不會出如今HTML中。

// 編譯前

//- 這是一個註釋
p 這是一個註釋

// 編譯後
<p>這是一個註釋</p>複製代碼
  • 塊級註釋
// 編譯前

//-
  註釋不會出如今模板中
  真的
//
  第一行註釋
  第二行註釋

// 編譯後

<!--
    第一行註釋
    第二行註釋
-->複製代碼
  • 條件註釋

對於條件註釋,Pug沒有任何特殊的語法,下面例子這是爲舊版本的Internet Explorer添加後備標記的特殊方法,可是因爲以<開頭的全部行被視爲純文本,普通的HTML樣式條件註釋將會很好。

// 編譯前
<!--[if IE 8]>
<p class="lt-ie9">
<![endif]-->

// 編譯後

<!--[if IE 8]>
<p class="lt-ie9">
<![endif]-->複製代碼
Conditionals條件語句
// 編譯前
- var user = {name: 'kobe'}
- var flag = true
#user
  if user.name
    h3.user-title #{user.name}
  else if flag
    p flag is #{flag}
  else
    p default   

// 編譯後
<div id="user">
  <h3 class="user-title">kobe</h3>
</div>複製代碼

Pug也支持另一個關鍵字 unless

// 編譯前
- var user = {name: 'kobe'}
#user
  unless !user.name
  h2 #{user.name}


// 編譯後
<div id="user">
  <h2>kobe</h2>
</div>複製代碼
doctype
// 編譯前

doctype html

// 編譯後

<!DOCTYPE html>複製代碼
Filters過濾器

過濾器可以讓你在Pug模板中使用其餘語言。也就是支持插件的使用,經過插件對模板內容進行過濾,處理,輸出.如scss,less,markdown,coffee-script....

先全局安裝這些插件

npm install --save jstransformer-coffee-script
npm install --save jstransformer-markdown-it複製代碼
// 編譯前

h2 MarkDown
  :markdown-it
    #### this is markdown filter
    [link](http://www.baidu.com)

  :coffee-script
    console.log('this is coffee-script');

// 編譯後

<h2>MarkDown</h2><h4>this is markdown filter</h4>
<p><a href="http://www.baidu.com">link</a></p>
    (function() {
  console.log('this is coffee-script');

}).call(this);複製代碼

缺點:不能支持動態內容或選項。

Includes包含

Pug容許你靜態包含一段 Jade, 或者別的存放在單個文件中的東西好比 CSS, HTML 很是常見的例子是包含頭部和頁腳。 假設咱們有一個下面目錄結構的文件夾:

- /index.jade
- /includes/
  -/head.jade
  -/footer.jade複製代碼
// index.jade
doctype html
html
  include includes/header.jade
  body
    h1 這是主題內容
    include includes/footer.jade複製代碼
// header.jade
header
  title 通用的header
  script(src='/jQuery.js')
  link(href='reset.css')複製代碼
// footer.jade
footer#footer
  p Copyright (c) foobar複製代碼
// 編譯後
<!DOCTYPE html>
<html> <header> <title>通用的header</title> <script src="/jQuery.js"></script> <link href="reset.css"> </header> <body> <h1>這是主題內容</h1> <footer id="footer"> <p>Copyright (c) foobar</p> </footer> </body> </html>複製代碼

include 能夠包含好比 HTML 或者 CSS 這樣的內容。給定一個擴展名後,Jade 不會把這個文件看成一個 Jade 源代碼,而且會把它看成一個普通文本包含進來:

// 格式

style
  include style.css
script
  include script.js複製代碼

甚至能夠經過include結合過濾器使用

// 引入article.md
include:markdown-it article.md複製代碼
模板繼承

Jade 支持經過 block 和 extends 關鍵字來實現模板繼承。 一個塊就是一個 Jade 的 block ,它將在子模板中實現,同時是支持遞歸的。

若是須要,Pug block 能夠提供默認內容,可是能夠經過block scripts, block content, 和 block foot來顯示以下所示的可選項。

// 基本使用

// 編譯前
block desc
  p 這是block context
block desc  

// 編譯後
<p>這是block context</p>複製代碼
// index.jade

doctype html
html
  include includes/header.jade
  body
    block content
    block foot
    .footer  some footer content複製代碼

如今要繼承上面那個index.jade,只需建立一個新文件,並使用extend指令,以下所示,給出路徑。 您如今能夠定義一個或多個block將覆蓋父塊內容的塊.

在Pug v1中,若是沒有給定文件擴展名,那麼.pug會自動附加到路徑上,可是在Pug v2中,這個行爲已被棄用。

// index.jade

doctype html
html
  block scripts
    script(src='/jquery.js')
  body
    block content
    block foot
    .footer  some footer content複製代碼
// page.jade

extends index.jade

block scripts
  script(src='/jquery.js')
  script(src='/page.js')

block content
  h2 page.jade
  - var pets = ['cat', 'dog']
  each petName in pets
    li=petName複製代碼
// page.jade 編譯後

<!DOCTYPE html>
<html> <script src="/jquery.js"></script> <script src="/page.js"></script> <body> <h2>page.jade</h2> <li>cat</li> <li>dog</li> <div class="footer"> some footer content</div> </body> </html>複製代碼

一樣能夠在一個子塊裏繼續添加塊,就像下面實現的塊 content 裏又定義了兩個能夠被實現的塊 sidebar 和 primary,或者子模板直接實現 content。

block content
  .sidebar
    block sidebar
      p nothing
  .primary
    block primary
      p nothing複製代碼

Pug容許你 替換 (默認)、 前置 和 追加 blocks. 使用 block append 或 block prepend 時 block 是可選的:

// pageTwo.jade

extend page.jade

append scripts
  script(src='/pageTwo.js')複製代碼
// 編譯後

<!DOCTYPE html>
<html> <script src="/jquery.js"></script> <script src="/page.js"></script> <script src="/pageTwo.js"></script> <body> <h2>page.jade</h2> <li>cat</li> <li>dog</li> <div class="footer"> some footer content</div> </body> </html>複製代碼
Interpolation插值
// 編譯前
- var author = 'xyz'
- var date = '2017-4'
h2
  p writer was by #{author.toUpperCase()}
  p date is #{date}

// 編譯後

<h2>
  <p>writer was by XYZ</p>
  <p>date is 2017-4</p>
</h2>複製代碼

若是你想保持#{}插值符號,可使用#{或者'\'.

Iteration迭代
  • each
// 編譯前
- var arr = [1,2,3,4]
each val,index in arr
  li= index + ':' + val 

// 編譯後

<li>0:1</li>
<li>1:2</li>
<li>2:3</li>
<li>3:4</li>複製代碼
  • while
// 編譯前
- var arr = 4
while arr > 0
  li= arr--


// 編譯後

<li>4</li>
<li>3</li>
<li>2</li>
<li>1</li>複製代碼
Mixins

Mixins容許您建立可重用的Pug block。

// 編譯前
mixin lists
 p this is a mixin block
+lists
+lists  

// 編譯後

<p>this is a mixin block</p>
<p>this is a mixin block</p>複製代碼

mixins能夠爲一個帶參數的函數

// 編譯前
mixin link(href,name)
  a(href=href)= name

+link('www.baidu.com','百度')  

// 編譯後

<a href="www.baidu.com">百度</a>複製代碼

mixins也可使用一個block來做爲內容

// 編譯前
mixin lists(names)
 p= 'my name is ' + names
 if block
   block
 else
   p not provided content
+lists('kobe')
+lists('cpul')
  p block content

// 編譯後

<p>my name is kobe</p>
<p>not provided content</p>
<p>my name is cpul</p>
<p>block content</p>複製代碼

未知數量參數(...)的mixins.

// 編譯前
mixin lists(className,...items)
  ul(class=className)
    each item in items
      li= item

+lists('demo',1,2,3)
// 編譯後

<ul class="demo">
  <li>1</li>
  <li>2</li>
  <li>3</li>
</ul>複製代碼
Tags

默認狀況下,一行開頭的文本(或僅在空格以後)表明一個html標籤。 縮進的標籤是嵌套的,建立了像html的樹結構。

Pug能夠判斷出哪些元素是自閉,您還能夠經過簡單地附加'/'字符來明確地本身關閉標籤:

爲了節省空間,Pug提供嵌套標記的內聯語法。

// 編譯前
p: span 內聯

// 編譯後
<p><span>內聯</span></p>複製代碼

Pug的缺點

凡事不可能完美.Pug也有本身的弊端.

  • 可移植性差
  • 對新手調試不方便
  • 性能不是很好
相關文章
相關標籤/搜索