[recovery mode] STAN — самый короткий шаблонный движок

imageХолодным Апрельским днем когда на Урале еще не растаял снег. Смеркалось. Я игрался с микро-шаблонами. К примеру: ejohn.org/blog/javascript-micro-templating/ Они все были сверхпроизводительны на пcевдо тестах, но в тоже время в них отсутствовал хоть какой либо более или менее серьезный функционал.

Последней каплей стало то что я пропустил js1k. One thing led to another. И в голову мне пришла интересная идея. Почему бы максимально не использовать возможности JS? Использовать синтаксис JS в шаблоне (что позволит с помощью JS движка парсить шаблоны) и использовать все возможности JS.

И получился шаблонный движок с довольно простым синтаксисом:

[TAG] raw (data: String) | variable [TAG] [TAG].b [TAG].e [TAG] raw (data: String) Что выглядит приблизительно так:

function _template () { div.b; span.context.value.span; span.raw (11).span; div.e; hr; raw ('plain text') } div.b → открывающийся тэг →

div.e → закрывающийся тэг →

div.context.value.div →

{{ context.value }}

hr → самозакрывающийся тэг →


Получается своего рода DSL.

И какого размера код? 30 строчек кода :) Я уж не говорю про минифицированную версию.Пример? // Данные — на самом деле в шаблон можно передать // любой JS обьект (включая примитивы) var data = [ { name: 'STAN' }, { name: 'Ai_boy' }, { name: 'IceFrog' } ];

// Главный шаблон function _template (){ // Через [ ] можно передать атрибуты нашему XML тегу h1['class=«head»'].raw ('List of names').h1;

for (var i = 0; i < context.length; i++) { // вызываем подшаблон partial(_item, context[i]); } }

// Partial — подшаблон function _item (){ b[args ({style: 'color: blue', class: 'test'})].raw («Name:»).b; div.context.name.div; hr; }

// Написание кастомных helper функций никогда // небыло настолько простым — просто пишем js function args (obj){ var result = ''; for (var key in obj) { if (obj.hasOwnProperty (key)) { result += key + '=»' + obj[key] + '» '; } } return result; }

document.body.innerHTML = STAN.run (STAN.compile (_template), data); Как начать? Можно зайти на сайт и поиграться в Sandboxaiboy.github.io/STAN/sandbox.htmlЛибо зайти на GitHub страницу и следовать инструкции в README.mdgithub.com/aiboy/STAN (использовать шаблонизатор можно как в браузере так и в Node.js)

В чем плюс? Главных приемущества ровно четыре:1) Полная поддержка JS синтаксиса и всех его возможностей (CoffeeScript, ClosureScript, TypeScript… ect)

2) Доступ к DOM в момент рендеринга шаблона.

3) Полная поддержка всех JS библиотек внутри шаблона (lodash, underscore, jquery… ect)

4) Поддержка шаблонов в любом текстовом редакторе — ибо они на самом деле представляют из себя чистый JS синтаксис

А скорость? jsperf.com/stan-speed-testimageСкорость «скомпилированного» шаблона (который потом вручную или автоматически превращен в обычный js файл) приблизительно равна скорости JavaScript:) Что весьма и весьма не плохо. Если динамически компилировать шаблоны то скорости увы не такие большие.

Почему не Zen Coding? Потому что Zen Coding не возможно выразить в рамках JS синтаксиса — тоесть Zen Coding — не может быть валидным JS.Это шутка? Несмотря на безумность/глупость (нужное подчеркнуть) идеи. Все весьма и весьма серьезно. Проект будет развиваться. Обрастать тестами, более правильным синтаксисом и многими другими плюшками. Заходите на GitHub страничку — оставляйте ваши пожелания, найденные баги и все прочее.PS: На самом деле я немного кревлю душой когда пишу что данный шаблонизатор состоит всего из 30 строк. Если честно отформатировать код то получится строк 40–50. Но для меня это больше психологический барьер которого я стараюсь придерживаться.

PPS: буду рад любым замечаниям по поводу «корректности и грамотности заметки» (, но будет лучше если все это будет написанно в личку)

© Habrahabr.ru