Pug, как заявлено, делает разметку более простой и читаемой. Достигается это за счёт упрощённого синтаксиса.
Синтаксис
В Pug нет закрывающих тегов, а сами теги пишутся без угловых скобок. Вложенность определяется отступами.
doctype html
html(lang="ru")
head
title Pug
body
h1 Pug - node template engine
#container.col
p.
Pug - языком шаблонов с акцент
на производительность и функции.
Такая разметка будет трансформирована в
<!DOCTYPE html>
<html lang="ru">
<head>
<title>PUG</title>
</head>
<body>
<h1>Pug - node template engine</h1>
<div class="col" id="container">
<p>
Pug - языком шаблонов с акцент
на производительность и функции.
</p>
</div>
</body>
</html>
Doctype
Для HTML5 достаточно короткой версии
doctype html
<!DOCTYPE html>
Другие варианты doctype для XML, strict и прочего смотрите на сайте pug https://pugjs.org/language/doctype.html
Doctype влияет на компиляцию. Например, конец самозакрывающихся тегов (/> >) или вывод логических атрибутов зависит от того, указан HTML или XML.
Если по какой-либо причине невозможно использовать ключевое слово doctype (рендеринг фрагментов HTML), но вы все равно хотите указать тип документа в шаблоне, вы можете сделать это с помощью параметра doctype.
let pug = require('pug');
let source = 'img(src="foo.png")';
pug.render(source);
// => '<img src="foo.png"/>'
pug.render(source, {doctype: 'xml'});
// => '<img src="foo.png"></img>'
pug.render(source, {doctype: 'html'});
// => '<img src="foo.png">'
Теги
По умолчанию текст в начале строки (или после пробела) представляет собой HTML-тег. Теги с отступом вкладываются, создавая древовидную структуру HTML.
ul
li Item A
li Item B
li Item C
<ul>
<li>Item A</li>
<li>Item B</li>
<li>Item C</li>
</ul>
Pug знает, какие элементы являются самозакрывающимися:
img
<img/>
Для экономии места, в Pug предусмотрен инлайн синтаксис для вложеных тегов
a: img
<a><img/></a>
Такие теги, как img, meta и link, автоматически закрываются (если вы не используете тип документа XML). Можно явно закрыть тег самостоятельно, добавив символ /.
foo/
foo(bar='baz')/
<foo/>
<foo bar="baz" />
Атрибуты
Атрибуты тегов в Pug похожи на HTML (с необязательными запятыми), но их значения являются обычным JavaScript.
a(href='google.com') Google
|
|
a(class='button' href='google.com') Google
|
|
a(class='button', href='google.com') Google
<a href="google.com">Google</a>
<a class="button" href="google.com">Google</a>
<a class="button" href="google.com">Google</a>
Javascript выражения тоже работают
- let authenticated = true
body(class=authenticated ? 'authed' : 'anon')
<body class="authed"></body>
Если у тега много атрибутов можно разделить их по строкам
input(
type='checkbox'
name='agreement'
checked
)
<input type="checkbox" name="agreement" checked="checked" />
Если имя вашего атрибута содержит необычные символы, которые могут мешать синтаксису JavaScript. Примеры таких символов включают [] и () (часто используется в Angular 2). В примере ниже `(click)` рассматривается как вызов функции вместо имени атрибута, в результате ошибка
div(class='div-class' (click)='play()')
/var/www/html/pug/Untitled-1.pug:1:11
> 1| div(class='div-class' (click)='play()')
-----------------^
Syntax Error: Assigning to rvalue
Либо заключите атрибут в кавычки, либо используйте запятые для разделения различных атрибутов.
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>
Далее будет несколько примеров того, как можно использовать переменные в атрибутах.
1. Записать атрибуты в Javascript
- let url = 'pug-test.html';
a(href='/' + url) Link
|
|
- url = 'https://example.com/'
a(href=url) Another link
<a href="/pug-test.html">Link</a>
<a href="https://example.com/">Another link</a>
2. Использовать шаблонные литералы
- let btnType = 'info'
- let btnSize = 'lg'
button(type='button' class='btn btn-' + btnType + ' btn-' + btnSize)
|
|
button(type='button' class=`btn btn-${btnType} btn-${btnSize}`)
<button class="btn btn-info btn-lg" type="button"></button>
<button class="btn btn-info btn-lg" type="button"></button>
По умолчанию все атрибуты экранированы, чтобы предотвратить атаки (например, межсайтовый скриптинг). Если вам нужно использовать специальные символы, используйте! = Вместо =.
div(escaped="<code>")
div(unescaped!="<code>")
<div escaped="<code>"></div>
<div unescaped="<code>"></div>
Булевы атрибуты принимают значения true и false. Если значение не указано, предполагается true.
input(type='checkbox' checked)
|
|
input(type='checkbox' checked=true)
|
|
input(type='checkbox' checked=false)
|
|
input(type='checkbox' checked=true.toString())
<input type="checkbox" checked="checked" />
<input type="checkbox" checked="checked" />
<input type="checkbox" />
<input type="checkbox" checked="true" />
Если doctype html, Pug знает, что не нужно указывать атрибут, и вместо этого использует краткий стиль (понятный всем браузерам).
doctype html
|
|
input(type='checkbox' checked)
|
|
input(type='checkbox' checked=true)
|
|
input(type='checkbox' checked=false)
|
|
input(type='checkbox' checked=true && 'checked')
<!DOCTYPE html>
<input type="checkbox" checked>
<input type="checkbox" checked>
<input type="checkbox">
<input type="checkbox" checked="checked">
Атрибут style может быть строкой, как любой нормальный атрибут; но это также может быть объект, который удобен, когда стили генерируются JavaScript.
a(style={color: 'red', background: 'green'})
<a style="color:red;background:green;"></a>
Атрибут class может быть строкой, как любой другой атрибут, но это также может быть массив имен классов, что удобно при генерации из JavaScript.
- let classes = ['foo', 'bar', 'baz']
a(class=classes)
|
|
//- атрибут класса также может быть повторен для объединения массивов
a.bang(class=classes class=['bing'])
<a class="foo bar baz"></a>
<a class="bang foo bar baz bing"></a>
Атрибут class может быть объектом, который отображает имена классов в значения true или false. Это полезно для применения условий в определении классов.
- let currentUrl = '/about'
a(class={active: currentUrl === '/'} href='/') Home
|
|
a(class={active: currentUrl === '/about'} href='/about') About
<a href="/">Home</a>
<a class="active" href="/about">About</a>
Классы можно задавать записывая название через точку после тега. Задавая класс для div, сам тег можно не указывать.
a.button
|
|
.content
<a class="button"></a>
<div class="content"></div>
ID элемента указывается как класс, только вместо точки используется #
a#main-link
|
|
#content
<a id="main-link"></a>
<div id="content"></div>
&attributes синтаксис может использоваться для разделения атрибутов элемента.
div#foo(data-bar="foo")&attributes({'data-foo': 'bar'})
<div id="foo" data-bar="foo" data-foo="bar"></div>
В приведенном выше примере используется литерал объекта. Но вы также можете использовать переменную, значение которой также является объектом.
- let attributes = {};
- attributes.class = 'baz';
div#foo(data-bar="foo")&attributes(attributes)
<div class="baz" id="foo" data-bar="foo"></div>
Атрибуты, примененные с использованием &attributes, автоматически не экранируются. Вы должны обязательно проверять любые пользовательские данные, чтобы избежать cross-site scripting (XSS).
- Войдите, чтобы оставлять комментарии