☰
Pug 模板语言速成指南:从缩进语法到 HTML 编译(learnxinyminutes-docs 德文版全解析)
2026/10/7 7:50:02 网站建设 项目流程
  • 文档
  • 教程

【免费下载链接】learnxinyminutes-docs

Code documentation written as code! How novel and totally my idea!

项目地址:https://gitcode.com/gh_mirrors/le/learnxinyminutes-docs
点击查看免费下载

Pug 是一门前端与后端通吃的模板语言,它以缩进代替尖括号,把可读的类 HTML 语法编译成标准 HTML,并内置 if 条件、循环、include 与 mixin 等能力,常作为 Node.js 服务端视图层模板引擎使用。本文以 learnxinyminutes-docs 仓库中的德文版教程 de/pug.md 为骨架,对照英文原文 pug.md 与葡萄牙语译文 pt-br/pug.md,逐段讲解 Pug 的注释、标签、属性、JavaScript 集成、循环、条件、包含与混入,读完你即可独立读懂并编写 Pug 模板。

一、Pug 是什么:一门编译为 HTML 的模板语言

德文版教程开篇即给出 Pug 的定位(de/pug.md):

Pug 是一门编译为 HTML 的小型语言(eine kleine Sprache, die zu HTML kompiliert)。它拥有更干净的语法,并附带 if 语句、循环等附加功能;同时也可以作为 Node.js 等服务器语言的服务端模板语言使用。

这段话包含三个核心事实:

  • 编译目标为 HTML:Pug 源码并非浏览器直接可执行的文件,而是经过编译生成标准 HTML 输出;
  • 语法更干净:无需书写<div></div>这类成对标签,仅用标签名加缩进即可表达层级;
  • 双场景适用:既能作为前端构建链路的 HTML 生成方案,也能作为 Express 等 Node.js 框架的服务端模板引擎(view engine)。

从文档示例可以推断出 Pug 的两条核心语法规则:缩进表达嵌套层级(同一缩进深度为兄弟节点,更深缩进为子节点),行内文本直接跟在标签名后。这是理解后续所有示例的基础。

值得一提的是,仓库为这篇教程提供了三种语言的版本:德文版 de/pug.md(本文主体)、英文原文 pug.md(最初版本,作者 Michael Warner)、葡萄牙语译文 pt-br/pug.md。三者代码骨架一致,仅变量命名与输出文案因语言而异,阅读时可互相印证。

二、文档结构与 frontmatter 约定

与仓库内其他教程一样,de/pug.md在 Markdown 正文之前有一段 YAML frontmatter,声明了本文档的元信息:

contributors: - ["Michael Warner", "https://github.com/MichaelJGW"] filename: lernepug.pug translators: - ["denniskeller", "https://github.com/denniskeller"]

其中filename: lernepug.pug(德语"学习 Pug")指定了本文档代码的下载文件名——网站会把正文代码块抽取拼接成可下载的.pug文件;translators字段记录译者。仓库的 CONTRIBUTING.md 明确规定:英文文章需要name与contributors字段,译文还需补充translators,且非英文文章会自动继承英文文章的 frontmatter 值——这正是德文版省略name: Pug的原因。这些约定由 lint/frontmatter.py 在提交时自动校验(允许的键为name、where_x_eq_name、category、filename、contributors、translators)。

三、注释:单行与多行

Pug 的注释语法以//-开头,不会被编译进最终 HTML(与 HTML 注释<!-- -->不同):

//- Einzeilenkommentar //- 单行注释 //- Mehrzeiliger //- 多行注释: Kommentar //- 续行只需保持缩进

要点://-后的内容直至该行结束均为注释;多行注释依靠缩进对齐延续,例如第二行Kommentar与首行Mehrzeiliger保持相同缩进即属于同一注释块。

四、标签(Tags):从基础到嵌套

4.1 基础标签与自定义标签

div //- <div></div> h1 //- <h1></h1> mein-benutzerdefiniertesTag //- <mein-benutzerdefiniertesTag></mein-benutzerdefiniertesTag>

Pug 中任何标识符都可以当作标签:div、h1等标准 HTML 标签自然成立,连字符命名的自定义标签(如mein-benutzerdefiniertesTag)也会原样编译为同名 HTML 标签——这对 Web Components 等自定义元素场景很有用。

4.2 兄弟节点与子节点

//- Geschwister(兄弟节点:同一缩进层级) div div //- <div></div> <div></div> //- Kind(子节点:更深缩进) div div //- <div> <div></div> </div>

这是 Pug 缩进语法的核心:同级缩进 = 兄弟节点,缩进加深 = 嵌套子节点。文档注释清晰地展示了二者的编译差异。

4.3 行内文本与多行文本

//- 行内文本:标签名后直接跟文本 h1 Hallo Welt //- <h1>Hallo Welt</h1> //- Multizeilentext(多行文本:标签名后加句点 .) div. Hallo Welt //- <div> Hallo Welt </div>

当标签后需要多行纯文本时,在标签名后加一个.(点号),其后的缩进块会被当作原样保留换行的文本内容,而不是子标签。

五、属性(Attribute):完整写法与简写

5.1 完整属性语法

属性写在标签名后的圆括号内,多个属性以空格分隔,字符串值用引号包裹,布尔型开关属性(如enabled)可裸写:

div(class="meine-klasse" id="meine-id" mein-benutzerdefiniertes-attr="data" enabled) //- <div class="meine-klasse" id="meine-id" mein-benutzerdefiniertes-attr="data" enabled></div>

注意mein-benutzerdefiniertes-attr(自定义 data 属性)会原样透传到输出,布尔属性enabled在 HTML 中不带值直接输出——这是 Pug 对 HTML 布尔属性的标准处理。

5.2 简写语法(Kurzhand)

Pug 提供了类 jQuery 的快速写法:.表示class,#表示id:

span.meine-klasse //- <span class="meine-klasse"></span> .meine-klasse //- <div class="meine-klasse"></div> div#meine-id //- <div id="meine-id"></div> div#meine-id.meine-klasse //- <div class="meine-klasse" id="meine-id"></div>

值得注意:只写.meine-klasse而不指定标签时,默认标签是div;多个简写可叠加(div#meine-id.meine-klasse),编译后class与id属性顺序由编译器规范化。

六、JavaScript 集成:让模板活起来

Pug 最大的特色之一是在模板中直接嵌入 JavaScript,以-前缀声明不输出的代码行。

6.1 单行与多行 JS

- const sprache = "pug"; //- 单行:- 前缀 //- 多行:单独的 - 后接缩进块 - const srache = "pug"; const cool = true;

带-前缀的语句仅执行逻辑、不产生任何 HTML 输出,用于定义变量、准备数据。

6.2 JS 生成 class 与 style

属性值可以直接引用 JS 变量:数组会自动展开为以空格分隔的 class 列表,对象会自动序列化为内联样式:

//- JS Klassen:数组 → class 列表 - const meineKlasse = ['class1', 'class2', 'class3'] div(class=meineKlasse) //- <div class="class1 class2 class3"></div> //- JS Stil:对象 → style 属性 - const meineStile = {'color':'white', 'background-color':'blue'} div(style=meineStile) //- <div style="color:white;background-color:blue;"></div>

6.3 &attributes 展开属性对象与动态布尔属性

若属性较多,可用&attributes(对象)一次性展开:

- const meineAttribute = {"src": "foto.png", "alt": "meine Bilder"} img&attributes(meineAttribute) //- <img src="foto.png" alt="meine Bilder">

布尔属性则由 JS 布尔值动态决定是否输出:

- let deaktiviert = false input(type="text" disabled=deaktiviert) //- <input type="text"> - deaktiviert = true input(type="text" disabled=deaktiviert) //- <input type="text" disabled>

同一模板、同一属性名,仅因变量值不同而输出截然不同的 HTML——这是服务端模板渲染表单控件的典型用法:false时省略disabled,true时输出disabled。

6.4 模板插值:#{...}与缓冲代码=

Pug 提供两种把变量写入输出的方式:

- const name = "Bob"; h1 Hi #{name} //- 插值:嵌入文本内部 h1= name //- 缓冲代码:整行输出变量值 //- <h1>Hi Bob</h1> //- <h1>Bob</h1>

#{表达式}用于在文本中插入值;标签= 表达式则把该表达式的结果作为标签的整个文本内容。

七、循环(Schleifen):each 的完整形态

德文版注释特别说明:each与for功能相同,教程统一使用each。

7.1 基本遍历

each value, i in [1,2,3] p=value //- <p>1</p> <p>2</p> <p>3</p>

语法为each 值变量, 索引变量 in 集合,索引变量可省略(i从 0 开始)。

7.2 同时使用值、索引与表达式

each value, index in [1,2,3] p=value + '-' + index //- <p>1-0</p> <p>2-1</p> <p>3-2</p>

p=value + '-' + index是完整的 JS 表达式缓冲输出,证明了循环体内可以使用任意 JS 运算。

7.3 空集合与 else 分支

each还支持可选的else分支,在集合为空时渲染:

each value in [] p=value //- (空集合:不产生任何输出) each value in [] p=value else p Keine Werte sind hier //- <p>Keine Werte sind hier</p>

对比两组示例可见:无else时空集合静默输出为空;有else时输出兜底内容。这在渲染"无数据提示"时非常实用。

八、条件(Bedingungen):if 与 case

8.1 if / else if / else

- const zahl = 5 if zahl < 5 p zahl ist kleiner als 5 else if zahl > 5 p zahl ist größer als 5 else p zahl ist 5 //- <p>zahl ist 5</p>

条件表达式为普通 JS 布尔表达式,分支块按缩进组织,最终仅有一支被编译输出。

8.2 case / when / default:模板版 switch

德文版用一个"订单状态"场景演示了case语句:

- const bestellungsStatus = "Ausstehend"; case bestellungsStatus when "Ausstehend" p.warn Deine Bestellung steht noch aus when "Abgeschlossen" p.success Bestellung ist abgeschlossen. when -1 p.error Ein Fehler ist aufgetreten default p kein Bestellprotokoll gefunden //- <p class="warn">Deine Bestellung steht noch aus</p>

此例同时展示了两个技巧:when的分支值既可以是字符串("Ausstehend")也可以是数值(-1);p.warn是标签 + class 简写的组合,等价于<p class="warn">。最终因为bestellungsStatus为"Ausstehend",仅输出警告分支。

九、Include:复用片段与静态资源

include指令把另一个文件的内容在编译期嵌入当前模板,是页面复用的基础手段。

9.1 包含 Pug 片段

假设导航片段文件includes/nav.pug内容如下:

//- File path -> "includes/nav.pug" h1 Firmenname nav a(href="index.html") Home a(href="about.html") Über uns

主模板index.pug中通过相对路径引入:

//- Dateipfad -> "index.pug" html body include includes/nav.pug //- <html> <body> <h1>Firmenname</h1> <nav><a href="index.html">Home</a><a href="about.html">Über uns</a></nav> </body> </html>

include的作用是把片段文件的内容原样拼接进当前模板的对应位置(相当于"文本级"合并),是头尾、导航、页脚等公共区块的标准复用方式。

9.2 导入 JS 与 CSS

include同样可用于把静态资源原样嵌入script与style标签:

script include scripts/index.js style include styles/theme.css

编译后 JS 文件内容会直接出现在<script>标签体内、CSS 内容出现在<style>标签体内——适合需要内联资源的小型页面场景。

十、Mixin:可复用的模板函数

Mixin 是 Pug 的"模板函数":用mixin 名称(参数)定义,用+名称(实参)调用。

10.1 无参 Mixin

mixin basic() div Hallo +basic("Bob") //- <div>Hallo</div>

注意此例的一个细节:basic未声明参数,因此调用时传入的"Bob"会被忽略,输出仍是<div>Hallo</div>。

10.2 带参 Mixin

mixin comment(name, kommentar) div span.comment-name= name div.comment-text= kommentar +comment("Bob", "Das ist super")

调用后应得到如下嵌套结构:

<div> <span class="comment-name">Bob</span> <div class="comment-text">Das ist super</div> </div>

这里有一个值得注意的仓库细节:德文版 de/pug.md 中+comment(...)后的注释误写成了<div>Hallo</div>,而英文原文 pug.md 给出了正确的完整输出。多语言文档互相对照,可以有效避免此类笔误造成的误解。Mixin 的实战价值在于:评论卡片、按钮、表单控件等重复出现的 UI 片段,只需定义一次、传参调用即可。

十一、仓库配套资源与延伸学习

  • 英文原文pug.md:内容骨架完全一致,变量名与文案为英文,是德文版与葡语版共同的"母本";
  • 葡萄牙语译文pt-br/pug.md:同样的代码结构,可用于对照不同语言下模板文案的本地化方式;
  • frontmatter 规范:CONTRIBUTING.md 说明了name、contributors、translators、filename等字段的约定,lint/frontmatter.py 是仓库的自动化校验脚本,可帮助你理解如何按仓库规范编写和提交新的模板语言教程;
  • 文档末尾的"Zusätzliche Ressourcen"(德文版 de/pug.md)指向 Pug 的官方网站、官方文档与 GitHub 仓库,是继续深入学习的入口。

小结

Pug 用一套简洁的缩进语法,把"标签、属性、文本、逻辑"统一进同一份模板://-注释、.class/#id简写、-与=的 JS 集成、each循环与else兜底、if/case条件、include片段复用、mixin模板函数——这些就是德文版教程 de/pug.md 的全部知识点。掌握它们之后,你既可以把它当作静态 HTML 的生成利器,也可以直接接入 Node.js 服务端渲染流程;当模板中出现中文、德文等多语言文案时,本文展示的三语对照(pug.md、de/pug.md、pt-br/pug.md)本身就是最佳实践参考。

  • 文档
  • 教程

【免费下载链接】learnxinyminutes-docs

Code documentation written as code! How novel and totally my idea!

项目地址:https://gitcode.com/gh_mirrors/le/learnxinyminutes-docs
点击查看免费下载

创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考

需要专业的网站建设服务?

联系我们获取免费的网站建设咨询和方案报价,让我们帮助您实现业务目标

立即咨询