company_banner

Yate: Яндекс.Почта перешла на новый шаблонизатор

    imageНекоторое время назад мы писали, что в Яндекс.Почте появился новый интерфейс, в котором используется шаблонизация данных в браузере. Немногие крупные сервисы отваживались на это, но мы и сейчас считаем такое решение наиболее удачным. Оно не только ускорило работу интерфейса, но и позволяет экономить трафик пользователя и эффективнее расходовать процессорное время серверов.

    Тогда в качестве шаблонизатора мы использовали XSL, а данные передавали в формате XML. Переведя проект на новый интерфейс, мы начали искать другие способы ускорения работы интерфейса Яндекс.Почты.

    Недавно мы перевели всю Почту на JS-шаблонизатор и JSON-данные.

    Причины отказа от XML/XSL
    Мы очень любим XSL, он выразительный, на нём действительно удобно писать шаблоны для крупных сервисов со сложными связями, большим количеством повторно используемых блоков и возможностью переопределять или доопределять блоки. Но есть у него и ряд существенных недостатков:

    • Не развивается
      Если посмотреть багтеркеры браузеров, то последние затронутые разработчиками упоминания об XSL датируются 2004 годом (особенно очевидна проблема в Хроме на графиках ниже).
    • Большое количество проблем в реализациях для различных браузеров
      Во-первых, реализации, как всегда, отличаются в IE и не в IE. Есть пара очень неприятных проблем в Опере, как, например, игнорирование первого xsl:call-template и сложными предикатами, а иногда — загрузка картинки до трансформации. Хром требует отличного от других браузеров xsl:output.
    • Сложно отлаживать
      Самым популярным способом диагностирования проблем является комментирование кусков шаблона.
    • Сложно профилировать
      XSL-процессор в браузере — чёрный ящик, и говорить о том, какие конструкции работают быстрее, а какие медленнее, можно только на основе косвенных суждений, полученных на синтетических тестах.
    • Cложно расширять
      Если использовать xslt на сервере, то там ещё можно подключить exslt, в браузере же приходится сильно исхитряться со стандартными средствами, чтобы как-то нестандартно обработать строки.
    • Трудно обрабатывать XML-данные на сервере
      Если нужно изменить выдачу перед попаданием на клиент, придётся использовать E4X – да, у нас spidermonkey. E4X на самом деле не очень удобный и уж точно не очень быстрый по сравнению с модификацией JSON.


    Выбор нового шаблонизатора
    Мы пробовали разные (как по семантике, так и по синтаксису) шаблонизаторы, в том числе: yate, handlebars, jade, dust и ajaxslt.

    Имея json-выдачу и все необходимые данные для формирования списка писем, мы попробовали использовать каждый из вышеперечисленных шаблонизаторов.

    Поскольку страница со списком писем использует наибольшее число из всех доступных составляющих почты (папки, метки, сборщики, фильтры, треды, ну и сами письма), мы сразу смогли проверить каждый шаблонизатор под максимальной нагрузкой на скорость работы/отрисовки. Также принимали во внимание удобство разработки и простоту поддержки кода в дальнейшем.

    Почти сразу стало очевидно, что императивные шаблонизаторы (handlebars, jade, dust) не могут сравниться по удобству разработки с декларативными, их код превращался в «кашу», в которой всё сложнее было разбираться. К тому же мы привыкли к гибкости XSL и сильному разграничению данных и логики отображения, поэтому нам было удобнее работать с шаблонизаторами похожей семантики.

    Таким образом, в финале оказались yate и ajaxslt. Но, несмотря на все старания наших разработчиков, ajaxslt не смог приблизиться к производительности yate и требовал больше 500 мс на преобразование.

    Итоговый зачёт по скорости отрисовки списка из 200 писем выглядел так:

    image

    Yate
    Yate — проект, созданный и развиваемый фронтэнд-архитектором Почты. Этот шаблонизатор уже успешно зарекомендовал себя на нескольких готовых, но ещё не представленных проектах Яндекса. Yate очень похож на XSL: при более лёгком и js-подобном синтаксисе в нём используются те же парадигмы (match, apply), поддерживаются предикаты, а также есть jpath — аналог XPath для навигации по JSON. Шаблоны компилируются в обычный javascript и использовать их можно как на клиенте, так и на сервере.

    Вот так выглядит один и тот же шаблон на XSL и на yate:

    image

    Для нас огромное значение имеет скорость работы интерфейса, поэтому мы были рады, когда yate показал очень хорошие результаты скорости рендеринга шаблонов — получилось, что реализованный на JavaScript процессор работает быстрее встроенного в браузер XSL-процессора. Кроме того, учитывая, что с каждой новой версией браузера JS становится всё быстрее и функциональнее, разрыв будет только увеличиваться.

    Только начав использовать yate, мы выиграли в скорости трансформации от 40% и более, в зависимости от браузера. В случае с Хромом выигрыш составил… 1200%!

    Но нам показалось, что этого недостаточно.
    Ведь скомпилированный шаблон – это обычный JS-код, который легко анализировать профайлером, имеющимся в любом браузере:

    image

    А это значит, что его можно исследовать и оптимизировать, добиваясь тем самым ускорения его работы.

    В итоге мы отыграли ещё пару миллисекунд, обнаружив и оптимизировав самые тяжёлые шаблоны, а также посмотрели, какие операции в скомпилированном шаблоне выполняются чаще всего, и подправили компилятор так, чтобы он сразу генерировал оптимальный для таких операций код:

    image

    Стоит отметить, что все исследования мы проводили на максимальном количестве писем на странице – 200. По умолчанию у пользователей 30 писем на странице, а на таких объёмах шаблонизация проходит ещё быстрее:

    image

    Существенно упростилась и отладка — если что-то прошло не так, достаточно вставить debugger в скомпилированный шаблон и посмотреть, в чём проблема. Также можно воспользоваться встроенной функцией log, выводящей в консоль браузера данные, на которые накладывается шаблон.

    Другим важным параметром является объём данных, которые грузит пользователь. В yate есть возможность разбивать шаблоны на модули и указывать зависимости между ними. Таким образом, модули можно подгружать по мере необходимости, а при трансформации указывать, какой именно модуль нужен, чтобы сгенерировать тот или иной кусок HTML.

    image

    Также в yate легко добавлять свои функции, например, для работы со строками или датами. Для этого достаточно задекларировать функцию, реализовать её на JavaScript и использовать:

    image

    Результат
    Яндекс.Почта была переведена на новый шаблонизатор за полтора месяца.
    Некоторые сервисы, используемые в Почте, еще не переехали на JSON, поэтому для них мы используем E4X процессор XML2JSON. Так как произошли и серьёзные архитектурные перестановки, то Диск, который пока остался на XSL/XML, теперь открывается только с перезагрузкой страницы. Но мы добились своей цели. Измерения показали, что мы не только не «просели» во времени загрузки Почты:

    image

    Но и существенно уменьшили время переходов по страницам внутри Почты:

    image

    Также мы получили гибкое, расширяемое и контролируемое нами решение, которое намерены развивать и совершенствовать.

    DIY
    Мы обязательно напишем, как использовать yate в ваших проектах. А если вы хотите попробовать yate уже сейчас, вам достаточно сделать npm install yate.

    В качестве документации можно использовать презентацию или вики про синтаксис и jpath. Также вам может понадобиться аналог XPath для JSON (jpath или no.path) и подсветка синтаксиса для vim или Sublime Text. Если у вас уже есть XSL-шаблоны, то вы сможете оценить, как будет выглядеть yate с помощью xsl2yate.
    Яндекс 526,89
    Как мы делаем Яндекс
    Поделиться публикацией
    Комментарии 185
    • 0
      Уже было подумал крутизна, но одна мысль мешает: какая его интеграция с поисковыми ботами? В смысле, на сколько хорошо они смогут парсить страницы?
      • –19
        Это странный вопрос. Робот получает уже готовый html.
        • +8
          Вроде как эти шаблонизаторы работают на клиенте.
          • +8
            Нет, в статье сказано, что шаблонизация происходит на стороне пользователя. Поэтому робот скорее всего не сможет нормально проиндесировать контент.
            • –3
              Даже в примере с меилбоксом шаблон сперва компилится в js, и потом подключается в html — не понятно, где тут шаблонизация на клиенте…
              • +3
                Компилируется в js, который потом уже лепит шаблон по правилам, видимо так
                • +3
                  Yate компилируется на сервере, а на клиент отправляются уже скомпилированные шаблоны, которые накладываются на JSON и дают HTML на выходе.

                  Ничего не мешает использовать компилированные шаблоны на сервере и отправлять на клиент сразу готовый HTML.

                  Компиляции на клиенте пока не предусмотрено, но так как компилятор тоже написан на JavaScript, то вполне возможно, что он будет портирован на клиент.
                  • 0
                    Т.е. это нифига не клиентское решение, большая часть работы все-равно происходит на сервере?
                    • +2
                      Шаблоны накладываются на данные на клиенте, но необходима предкомпиляция шаблонов в JS, которая делается на сервере.
                      • –4
                        Ну, так не интересно…
                        • +6
                          Скомпилировать шаблон — это разовая операция, которую надо выполнить при подготовке кода для продакшена. Это как обфускация js и препроцессинг CSS из LESS, Stylus.
                          • –2
                            Зачем тогда там компилировать шаблоны, почему бы просто старую добрую статику не отдавать?
                            • +6
                              Шаблон описывается на мета-языке разметки, который удобный человеку. Затем, единожды, компилируется в plain js — который весь такой оптимизированный и быстрый, но совершенно не читабельный. Вот этот plain js — из json делает HTML. Причем умеет это делать как на клиенте так и на сервере.
                      • 0
                        Шаблоны можно скомпилировать один раз.
                        • –6
                          Если можно использовать статичные шаблоны, тогда и компилировать вообще ничего не надо, достаточно старого доброго статичного html.
                          • 0
                            А в какой ситуации могут понадобится динамические шаблоны? По-моему сама идея шаблонов подразумевает, что есть какая-то неизменная часть и места, куда надо подставлять изменяющиеся данные. Или я не понял, что вы имеете ввиду.
                            • –6
                              Как в какой? Да хоть бы разное количество писем отрисовать. Циферку «У вас $N писем» вставит скрипт на клиенте. А разное количество строк с этими письмами кто будет отрисовывать? Строки таблицы кто будет в цикле генерировать?

                              И Вы не ответили — почему не статика?
                              • +1
                                Вы не улавливаете сути. Есть некоторый шаблон на Yate, он преобразуется в «шаблон» на javascripte (на сервере), именно этот «шаблон» заполняется полученными данными из JSON (на клиенте). И это происходит динамически на клиенте (заполнение). И уже в зависимости от полученных данных (JSON), у вас сформируется нужной кол-во строчек в списке писем, ну или что вам там нужно будет.
                        • +1
                          Судя по файрбагу сейчас как раз сделали все на клиенте. Приходит джейсон, на основе которого строится клиентская часть. Сейчас приходит анонимная функция, которая сформирована на сервере(там по факту под имя шаблона сформированный js для формирования dom), и уже она формирует гуй. т.е. передав один раз шаблоны при старте клиента, потом только передают опции в функцию с шаблоном для отрисовки dom с этими новыми данными. все кэшируется, все быстро в принципе работает.
                          • –2
                            Автор выше пишет, что что-то компилируется на сервере. Что?
                            • 0
                              Шаблон компилируется на сервере, формируя Javascript код функции, которая позже на клиенте будет получать данные из джейсона и формировать dom модель для отображения.
                              • –6
                                Я теряю нить. То Вы говорите, что всё на клиенте, то Вы компилируете шаблон на сервере.
                                • +3
                                  Возможно я путанно выражаюсь. На сервере пишется шаблон на каком нть мета языке, он компилируется создав джаваскрипт и отдается на клиент. на клиенте уже данная функция запускается. В нее скорее всего передается имя шаблона, который надо сформировать и пришедшие от сервера опции (скажем список писем в джейсоне) а функция эта по шаблону формирует и возвращает dom, которую просто надо подставить на место.
                                  • 0
                                    Шаблон пишется на Yate, Yate компилируется в JS на сервере (1 раз), готовый скомпилированный JS отдаётся клиенту вместе с JSON данными (каждый раз по запросу, точнее JS отдаётся при загрузке страницы, JSON при обновлении списков), которые и визуализируются в HTML. Все же просто.
                                    • 0
                                      Зачем обязательно на сервере-то? Можно деплоить продакшен после преобразований Ant/Capistrano/Phing.
                                      У меня например нет и не предвидится желания запускать что-то вроде node на большинстве клиентских серверов. А вот на рабочей машинке все имеется.
                        • +4
                          А зачем индексировать закрытые разделы, такие как почта?
                          • –2
                            Вы действительно думаете что вам скажут правду? :) Для вашего же блага, очевидно :)
                        • 0
                          Можно использоывать один и тот же язык шаблонов на стороне клиента и сервера (например mustache). При первичной заргузке рендерим на сервере, а дальше, получая данные AJAX запросами, на клиенте.
                        • 0
                          Не все роботы работают с js. Создание html происходит на стороне клиента из полученого сначала js файла и запрашиваемых json данных, готового (полностью) html нету
                          • 0
                            Да кто же вам мешает отдавать готовый HTML?
                            Почту то индексировать не нужно… поэтому и выгодно перебросить шаблонизацию на клиент.

                            Да и вообще можно отдавать для поисковых ботов сгенерированные HTML, а обычным юзерам JSON… И этого вам тоже никто не запретит… С таким решением конечно же есть проблемы, URI например, но это возможно!
                            • 0
                              > Да и вообще можно отдавать для поисковых ботов сгенерированные HTML, а обычным юзерам JSON

                              Не уверен в SEO-экологичности такого клоакинга.
                              • 0
                                Да, с этим проблема! Так как если роутинг делать на клиенте в адресной строке браузера будет хреновая(не валидная для ботов) ссылка.
                                • +1
                                  Для решения этой проблемы есть History API. Например так сделано на GitHub. Попробуйте походить по дереву каких-нибудь исходников. Подгрузка идет через ajax, но адрес меняется как обычно.
                                  На хабре как раз была статья как это реализовано у них.
                                  • 0
                                    Значит нет никаких проблем… Можно равняться на GitHub!
                        • +2
                          Статья про шаблонизатор. Какую связь вы уловили с поисковыми роботами?
                          • +12
                            Вероятнее всего, romy4 хотел бы заюзать этот шаблонизатор на сайте, который индексируют поисковики.
                            • +2
                              В контексте почтового ящика связи действительно никакой.

                              Но в других случаях связь прямая — если все данные подгружаются динамически или вываливаются в виде JS-объекта, то могут быть проблемы
                              • +1
                                Теперь понял. Это общая проблема сайтов, которые устроены как JS приложение.
                                Остаются только meta описания.

                                Yate можно использовать на сервере, а не на клиенте.
                                • +4
                                  Ну почему. Можно при запросе страницы заполнять темплейт первичными данными и отдавать клиенту готовый HTML. А потом уже подгружать, сортировать, воровать и убивать.
                                  • НЛО прилетело и опубликовало эту надпись здесь
                              • 0
                                Думаю при разработке сервисов — индексация это последнее о чем вы будете думать.
                                Или ваша личная почта доступна поисковым роботам?
                                • –1
                                  Я не думаю, что это чисто почтовый шаблонизатор, хотя бы исходя из:
                                  Этот шаблонизатор уже успешно зарекомендовал себя на нескольких готовых, но ещё не представленных проектах Яндекса.

                                  Поэтому интересна его интеграция в открытый проект.
                                  • 0
                                    Мне кажется вы возлагаете на шаблонизатор те функции, которые он исполнять не должен.
                                    Я говорил не про конкретно почту, а про «услуги как сервис», где индексация поисковиками даже вредна.
                                    • 0
                                      Какие функции я на него возлагаю? Но я не говорил про сервис.
                                      • 0
                                        Индексация поисковиками.
                                        • –1
                                          Правильно, готовая страница, созданная шаблонизатором должна быть проиндексирована. Если шаблонизатор этого не делает, значит надо так и сказать. Зачем вы рассказываете про сервисы?
                                          • +1
                                            Мы с вами явно не подружимся :)

                                            — если сервер отдает готовый html, поисковику все равно чем вы там страницу собираете
                                            — если интерфейс собирается на клиенте, поисковику опять все равно, т.к. исполняется только простейший js, и ваша страница не индексируется.

                                            Для решения этой задачи был придуман hash-bang, но задача шаблонизатора, шаблонизировать собственно, а не заниматься всем и вся.
                                • НЛО прилетело и опубликовало эту надпись здесь
                                • –1
                                  Какие роботы вы хотите, чтобы сканировали вашу почту? Шаблонизатор клиентский с большой долей вероятности пригодится в web-приложениях, не требующих сканирования себя роботами.
                                • –6
                                  Яндекс же в w3c! Какие проблемы, примут синтаксис шаблонизатора как новый язык разметки, и всего-то делов.

                                  Хотя, конечно, хорошим окончанием рассказа про шаблонизатор стало бы («станет», т.к. рассказ был про «почту», про шаблонизатор обещают же рассказать) упоминание, что Яндекс научился индексировать страницы на этом шаблонизаторе, но как-то не верится…
                                  • 0
                                    Простите мой китайский, но на хуа думать о поисковиках, когда инструмент предполагается больше использовать в закрытом пространстве, где сначала идет аутентификация?
                                  • 0
                                    Не вижу никаких проблем, гугль и другие поисковики уже умеют индексировать ajax-сайты, причём делают это достаточно хитро: по имеющейся «ajax-ссылке» (что-то вроде mysite.ru/#!/link/89) они формируют нормальную ссылку без хэша, по которой сервер отдаёт готовый HTML-слепок ajax-страницы.
                                    • 0
                                      Я тоже не вижу, но а) покажите сводную табличку о том, что умеют парсить поисковики. Мне как-то на глаза не попадалась; и б) речь конкретно об этом шаблонизаторе
                                      • 0
                                        Вот вам как это делает гугль: developers.google.com/webmasters/ajax-crawling/docs/getting-started
                                        при желании можете поискать как это делают другие поисковики (но лично мне кажется, что примерно так же).
                                        Что касается шаблонизатора — не имеет никакого значения какой он, поскольку HTML берётся с сервера уже готовый, в обход клиентской инфраструктуры.
                                  • +1
                                    Просмотрел код — не понятно, как использовать шаблоны на клиенте, без пре-компиляции на сервере. Или это не предусмотрено?

                                    Просто XSL компилится на клиенте…

                                    Сорри, если туплю. Документацию надо, без нее сложно.
                                    • 0
                                      Просто XSL компилится на клиенте…

                                      Судя по всему, Вы никогда не работали с XSL. Его можно компилить как на сервере (отдавая клиенту готовую html-страницу, так и на клиенте.
                                      • 0
                                        Работал, и работаю. И ищу замену. Мы компилим на клиенте, т.к. серверный компайл неимоверно грузен.
                                        • –2
                                          Если он настолько неимоверно грузен, как Вы говорите, то Вы что-то делаете неправильно.
                                          • +5
                                            Действительно неправильно — используют XSL
                                            • 0
                                              Большинство шаблонизаторов медленнее XSLT, но это не мешает их использовать. Yate это интересная разработка, но он мало где пригодится, раз только используется на клиенте.
                                              • 0
                                                С чего вы взяли, что только на клиенте?
                                                Шаблоны компилируются в обычный js — так что можно использовать хоть в node.js, хоть в чем еще.
                                                • 0
                                                  Ну то что в node.js это можно использовать я не сомневался :) А где еще, в PHP/Perl/Python можно?
                                                  • 0
                                                    Ну ноде серверный js не заканчивается. Хотя, конечно, нода наиболее популярна.
                                                    Плюс v8 можно использовать и напрямую. Например, из перла/питона/…
                                                    • 0
                                                      ноде -> нодой
                                                      • 0
                                                        Интересно было бы посмотреть серверные тесты такой шаблонизации, по сравнению с XSLT.
                                      • +4
                                        Очень рад, что вы начинаете подчищать атавизмы :).
                                        • 0
                                          Грустно это признавать, но Вы правы. XSL действительно устарел и надо думать о чём-то новом.
                                          *задумчиво чешет в затылке, размышляя сколько времени необходимо для того, чтобы перевести свои проекты на yate*
                                          • 0
                                            Я слышал, что Яндекс ещё не перешёл на препроцессоры. Хотя может Яндекс.Почта уже перешла — там живенько всё.
                                            • +6
                                              Да, в Почте уже перешли на Stylus. Не целиком, конечно, — перевести код с таким наследием за один раз практически невозможно.

                                              Сейчас больше половины старых блоков подключается импортами в css, но все новые блоки уже сразу пишутся на стайлусе, ну и как только какой-то блок надо подправить — он также переводится на стайлус. Плюс, новые темы для Почты также делаются, используя стайлус. Процесс идёт :)

                                              Подробнее про переход на стайлус я когда-нибудь (как смогу найти на это время) напишу статью в наш блог по разработке интерфейсов.
                                              • 0
                                                Это было бы очень интересно, а то всё Сасс, да Лесс.
                                                • +1
                                                  А почему кстати Stylus, а не сасс и лесс?
                                                  • +4
                                                    По этой теме много чего можно рассказать, но если кратко:

                                                    — Sass отличный, но он а) на руби, б) имеет местами излишне громоздкий синтаксис (для `.scss`), в) не поддерживает конкатенацию с parent reference (типа `&__element`).

                                                    — Less — очень-очень слабый, как-то спасает возможность внутри использовать js, но в целом он очень простой. Его сильная сторона — низкий порог входа, но когда нужно сделать что-то не банальное, его возможностей не хватает.

                                                    — Stylus — как и Less работает на js — у нас и так всё на нём, для нас это преимущество. Он очень гибкий и позволяет делать много сложных штук. Если сравнивать по функциональности с Sass, то он в чём-то и проиграет, но большинство минусов для нас не имеют значения. Зато у Стайлуса прозрачный синтаксис миксинов — не нужно учить новый синтаксис для префиксных свойств, просто подключаешь библиотеку с миксинами и всё будет работать.

                                                    А вообще, самый простой способ понять какой препроцессор использовать — взять какой-то свой проект и по очереди переписать весь CSS на разных препроцессорах — максимально используя их возможности. Сразу станет ясно что подходит, а что — нет :)
                                                    • +2
                                                      Спасибо за развернутый ответ!
                                                      Совет, конечно, прекрасный, но обычно малоосуществимый.
                                                      • 0
                                                        >> в) не поддерживает конкатенацию с parent reference (типа `&__element`)

                                                        Это типа такую &:element? Или как?
                                                        • 0
                                                          Именно `&__element`, т.е. когда не псевдокласс или псевдоэлемент присобачиваются к родительскому, а часть имени.

                                                          В Less и Stylus `&__element` внутри `.block` даст `.block__element`, а в Sass там появится пробел между ними — и править это разработчики не собираются.
                                                        • 0
                                                          И вот еще что, есть же libsass, так что обязательной привязки к руби нету.
                                                          • 0
                                                            С/С++ — тоже не JS. Кроме того, любые неофициальные порты будут отставать в версиях от оригинала. Какая версия Sass реализована сейчас в livsass? Я с ходу этой информации в репозитории не нашёл.
                                                            • 0
                                                              Там где C, до модуля ноды рукой подать, у sass вроде нет версий спецификации так что я затрудняюсь сказать, знаю лишь, что планируется замещение обычного sass на обертку поверх libsass. Но когда оно будет, никто не знает.
                                                              • 0
                                                                Ну, у оригинальной имплементации Sass есть ченджлог + в репозитории есть все версии как по тегам, так и соответствующих файликах типа VERSION. Хорошо бы и в сторонних реализациях как-то указывать, с какими версиями они совместимы.
                                            • +4
                                              XSL прекрасно отлаживается в студии. По нажатию F5 выбирается файл XML, после чего F10 и F11 позволяют дебажить в стандартном режиме, без и с заходом в функции (шаблоны).
                                              • 0
                                                А это закрытое решение или где-то в открытом доступе есть?
                                                • 0
                                                  Я по работе в Professional сижу, так что не могу вам однозначно сказать насчет того есть ли такая возможность в Express версии. Если есть желание можете попробовать.
                                                  • +2
                                                    Люди без винды оказались не у дел.
                                                    • 0
                                                      в IntelliJ IDEA есть XSLT-debugger (правда я им сам ни разу не пользовался)
                                                • 0
                                                  Вы же понимаете, что отладить код в одном единственном XSLT-процессоре — это как отладить верстку в одном единственном браузере?
                                                  • 0
                                                    Для веб-разработчиков, да, понимаю. Но мне к счастью не приходится заниматься интерфейсами, и использую только один процессор, поведение которого предсказуемо (msxsl).
                                                • –4
                                                  Предложения по почте для доменов:

                                                  1. Упорядочить ящики по алфавиту. При добавлении адресов в рассылку убрать постраничное деление и добавить графу Ф.И.О., логины пользователей не всегда очевидны.

                                                  2. В списке почтовых ящиков ввести графу с датой последней активности (помогает вычислять неактивные ящики) и вообще сделать его более информативным. Например указать рассылки в которых ящик состоит.

                                                  3. Сделать оповещатель о новой почте для трея. «Швейцарский нож» Я.онлайн не предлагать.

                                                  4. Добавить возможность прикреплять к письму сразу несколько файлов.

                                                  5. Удалённый ящик не исчезает из списка рассылки, после чего почта сама себе начинает рассылать уведомления о недоставленом письме.
                                                  • 0
                                                    Было бы интересно узнать, сколько такая оптимизация экономит времени пользователям.
                                                    Например:
                                                    Количество открытий почты по браузерам, за день x Сэкономленное время на странице -> PROFIT!

                                                    PS: теперь понимаю, почему мне не нравилось пользоваться Я.Почтой в Chrome
                                                    • 0
                                                      Скорее — на сколько удалось понизить кол-во отказов до момента полной загрузки страницы.
                                                      • 0
                                                        Можно и так, но я ожидал в конце увидеть что-нибудь маркетинговое, вроде «Это ежедневно экономит ХХХ минут/часов пользователям Яндекс.Почты»
                                                        • 0
                                                          Вот честно, не представляю себе, чтобы таска на ускорение рендеринга страницы исходила из необходимости написать один пресс-релиз :)
                                                          • 0
                                                            А вот снижение отказор уже больше тянет на коммерческую задачу — больше юзеров загрузит страницу полностью — больше раз покажется баннер.
                                                            • +1
                                                              С одной стороны вы правы, должна быть коммерческая цель.
                                                              Но с другой стороны — важны довольные/счастливые пользователи, жизнь которых становится лучше (меньше времени тратится на рутинные задачи). А если это еще и соответствует коммерческим целям — просто замечательно!
                                                              Мне, как пользователю, важнее раньше увидеть заголовки писем. А дождался я полного рендера/загрузки — мне не важно.
                                                            • +2
                                                              есть считать только ускорение отрисовки списка писем — то это экономия времени около 7 часов в день, если взять во внимание всю оптимизацию, то часов 14, наверное
                                                              • 0
                                                                НО у каждого клиента при этом экономится несколько милисекунд. Если говорить о скорости авторизации и выдачи юзеру списка писем, то у КОГО УГОДНО дела лучше, чем у Gmail :)

                                                                Я понял основную причину перехода на новую технологию как уход со старого стремного XSL на новый крутой Yate.
                                                                • +1
                                                                  экономия для каждого пользователя 30-100 мс за каждый клик
                                                              • +2
                                                                По предварительным подсчётам вчера мы сэкономили нашим пользователям больше месяца времени.
                                                          • 0
                                                            Пара вопросов:

                                                            — можно ли запускать на сервере? Если да — только node.js? Не планируется ли компилятор, например, в java, как у Google в Closure Templates?

                                                            — не планируется ли какая-либо автоматизация привязки DOM к JS при вставке шаблона?
                                                            Я такое видел в dojo, удобно. Что-то вроде такого: в шаблоне помечаем нужные для JS-логики ноды, а при вставке автомагически вызывается нужный JS, в который передаются эти ноды. Обычно ведь как — вставляем HTML, и потом ищем в том что вставилось все нужное запросами — это неудобно и есть дублирование кода, есть риск что шаблон поменяют, а селекторы забудут. Хочется чего-то декларативного.
                                                            • 0
                                                              Да, можно запускать на сервере, только nodejs, на языки, отличне от JavaScript транслировать компилятор не планируется.

                                                              Остальные вопросы скорее про используемый фреймворк, а не про шаблонизатор, не думаю, что шаблонизатору нужны все эти функции, так что нет, пока не планируется.
                                                              • +1
                                                                Вообще-то планы по компиляции шаблонов не только в js есть.
                                                                Сейчас почти весь генерируемый код описан в отдельном файле-шаблоне.
                                                                Пока что, к сожалению, не все вынесено туда, но в будущем будет все там.
                                                                Так что можно будет сделать компиляцию во что-то еще.
                                                                Не уверен насчет именно java, но там видно будет.
                                                              • +2
                                                                А Вы пробовали сравнить с Fest от мейл.ру? Я далеко не сторонник синтаксиса в духе XSLT, но в своём классе этот шаблонизатор действительно быстрый. У Вас в результатах бенчмарков цифры (сужу по Chrome) великоваты. На большинстве страниц адекватного размера быстрые шаблонизаторы вполне укладываются в 1мс на рендеринг из уже скомилированной функции, если она достаточно оптимальна.
                                                                • 0
                                                                  У Fest же нет рантайма в браузере
                                                                  • 0
                                                                    Он точно также компилирует XSL-подобный синтаксис в JS-код. Передать этот код в браузер задача тривиальная.
                                                                    • 0
                                                                      Это не XSL-подобный синтаксис. Fest — обычный replacer, типа mustache или handlebars. Нам такие шаблонизаторы сразу не подошли.
                                                                      • 0
                                                                        А чем именно не подошли? Сложность в переписывании тонны кода старых шаблонов (хотя Вам всё равно, скорее всего, пришлось это сделать) или просто идеологическая не предрасположенность? В Вашем случае, с учётом количества пользователей ресурса, чтобы пренебрегать возможностью сделать раз в 5-10 быстрее нужны довольно веские причины.
                                                                        • 0
                                                                          Тем, что нет аналога xsl'ного apply-templates и предикатов в матчах шаблонов. Без этого наша тонна кода превратится в неподдерживаемую кашу.
                                                                          • 0
                                                                            Ну если только так, как решение чтобы не убиться о старый код. Если рендерить страницы из таких функций на сервере через node.js и функция рендеринга будет работать 6-16мс, то придётся запускать сильно больше инстансов ноды, т.к. процесс лочится на время выполнения блокирующего кода, коим является рендеринг. Это очень не экономно, т.к. многие другие шаблонизаторы гененрируют функции, которые выполняются менее 1мс.
                                                                            • 0
                                                                              … чтобы не убится об новый код. Простейшие реплейсеры как раз приведут к тому, что у нас будут не шаблоны, а каша.

                                                                              И мы не рендерим страницы на сервере, а рендерим их на клиенте.
                                                                              • 0
                                                                                Получилось довольно узкое решение, а «каша» это понятие очень субъективное. Многим нравятся Haml/Jade подобные синтаксисы, комуто XSL-подобные. Мне, например, больше нравятся синтаксисы в духе EJS/Eco. Я только вчера публиковал статью о JS шаблонизаторе.
                                                                                Тут не суть. В любом случае в конце концов получается функция конкатенации строки. У Вас она работает сильно дольше чем у других.
                                                                                • 0
                                                                                  Конкатенация разная бывает.
                                                                                  У простых шаблонизаторов — это линейная склейка строк + if/for.
                                                                                  У xsl/yate это выбор, в зависимости от данных, что дальше склеивать.

                                                                                  Первый вариант работает мега-быстро, но при увеличении числа шаблонов, количества переопределений, появления common'а и вызова его из разных мест, код превращается в кашу.

                                                                                  Второй вариант работает медленнее, зато у него легкая поддержка и простота работы с большим числом шаблонов.
                                                                                  • 0
                                                                                    Код превращается в кашу не из за шаблонизатора, а из за того кто пишет шаблоны (естественно, если не использовать совсем простые шаблонизаторы). Наследование, инъекция и блоки, в большинстве случаев, задачу решают и поддерживаются уже несколькими различными шаблонизаторами. При этом функция остаётся «мега-быстрой». У меня всё же впечатление что тут играет роль именно дело привычки, т.к. Вам удобен подход именно с apply-templates.
                                                                                    • 0
                                                                                      Ок, я с вашим аргументами согласен, но все-таки попробую переубедить :)

                                                                                      Давайте разберем пример. Есть массив, каждый элемент надо отрисовать по-разному, в зависимости от типа.
                                                                                      <items>
                                                                                        <item type="1"/>
                                                                                        <item type="2"/>
                                                                                        <item type="1"/>
                                                                                        ...
                                                                                      </items>
                                                                                      


                                                                                      в xsl мы пишем
                                                                                      <xsl:template match="items">
                                                                                        <xsl:apply-templates/>
                                                                                      </xsl:tempate>
                                                                                      
                                                                                      <xsl:template match="item">
                                                                                        <!-- общий html -->
                                                                                      </xsl:tempate>
                                                                                      
                                                                                      <xsl:template match="item[@type = 2]">
                                                                                        <!-- переопределение -->
                                                                                      </xsl:tempate>
                                                                                      


                                                                                      Т.о. добавление нового типа простое и понятное, тем более, что такой шаблон можно написать в любом месте (хоть сторонний код) и все будет работать.

                                                                                      Как это реализовать на вашем любимом шаблонизаторе?
                                                                                      • 0
                                                                                        Обычно создают карту обработчиков в зависимости от type и используют как декораторы.
                                                                                        • 0
                                                                                          т.е. все типы надо знать заранее?
                                                                                          • 0
                                                                                            Как правило + дефалты. Да и глупо сравнивать императивные и декларативные шаблонизаторы.
                                                                                        • +1
                                                                                          К примеру так:

                                                                                          <items>
                                                                                            <% for item in @items : %>
                                                                                              <% switch item.type : %>
                                                                                          
                                                                                                <% when 2 : %>
                                                                                                  <!-- переопределяем -->
                                                                                                <% end %>
                                                                                          
                                                                                                <% else : %>
                                                                                                  <!-- общий html -->
                                                                                                 <% end %>
                                                                                          
                                                                                              <% end %>
                                                                                            <% end %>
                                                                                          </items>
                                                                                          


                                                                                          Или так:

                                                                                          <% renderItem = (item) -> %>
                                                                                            <% switch item.type : %>
                                                                                          
                                                                                              <% when 2 : %>
                                                                                                <!-- переопределяем -->
                                                                                              <% end %>
                                                                                          
                                                                                              <% else : %>
                                                                                                <!-- общий html -->
                                                                                              <% end %>
                                                                                          
                                                                                            <% end %>
                                                                                          <% end %>
                                                                                          
                                                                                          <items>
                                                                                            <% for item in @items : %>
                                                                                              <%- renderItem item %>
                                                                                            <% end %>
                                                                                          </items>
                                                                                          


                                                                                          А вообще гораздо чаще встречается ситуация, когда надо изменить не весь шаблон в зависимости от типа. А, например, добавить класс ссылке или строке таблицы. Вот тут в XSL придётся как минимум 3 строки кода добавить:

                                                                                          <a href="{item/url}">
                                                                                            <xsl:if test="item/current = 1">
                                                                                              <xsl:attribute name="class">current</xsl:attribute>
                                                                                             </xsl:if>
                                                                                            <xsl:value-of select="item/name" />
                                                                                          </a>
                                                                                          


                                                                                          вместо:
                                                                                          <a href="<%- item.url %>" <% if item.current%>class="current"<% end %>><%- item.name %></a>
                                                                                          


                                                                                          А если ещё нужно добавлять другие классы при этом в зависимости от разных условий то код ещё больше разнесет.

                                                                                          В моём примере когото могут смутить разделители, но они по вкусу настраиваются. Например можно так:

                                                                                          <a href="{{-item.url}}" {{if item.current}}class="current"{{end}}>{{-item.name}}</a>
                                                                                          

                                                                                          • 0
                                                                                            А если таких типов 10? Громандный switch?
                                                                                            А как их объявить в разных местах?
                                                                                            • 0
                                                                                              Если таких типов 10 и они все требуют своего html кода, то делается 10 шаблонов для каждого типа элемента. И выбирается нужный:

                                                                                              <items>
                                                                                                <% for item in @items : %>
                                                                                                  <% partial 'items/item_' + item.type, item %>
                                                                                                <% end %>
                                                                                              </items>
                                                                                              
                                                                                              • 0
                                                                                                а как в вашем примере сделать дефолтный шаблон для 5-и типов из 10?

                                                                                                а если есть type и subtype?
                                                                                                match=«item[type = 1]»
                                                                                                match=«item[type = 2]»
                                                                                                match=«item[type = 2 and @subtype = 1]»
                                                                                                match=«item[type = 3 and @subtype = 4]»
                                                                                                • 0
                                                                                                  Это синтетические примеры, опирающиеся на сильные стороны XSLT. Так что угодно можно подогнать. В каждом конкретном случае используется техника написания под особенности конкретного синтаксиса. У XSLT есть свои минусы и самый большой из них — производительность и избыточность синтаксиса. Чего только стоит disable-output-escaping=«yes» против «черточки» и «равно» у конкурентов.
                                                                                                  • 0
                                                                                                    К примеру в mako (который тоже не декларативный шаблонизатор, хоть и для Python) есть конструкция if,elif,else куда ваш пример великолепно ложится.
                                                                                                    Кроме того никто не запрещает создавать шаблонные функции и красиво выносить обработку таких вещей туда. Мне кажется для JavaScript такое тоже можно вполне написать.
                                                                                                    • +1
                                                                                                      Кстати, ещё один камень в огород XSLT то, что на входе он ожидает XML данные, а в XML их ещё нужно собрать. В один прекрасный день, профилируя производительность скриптов мы обнаружили, что большая часть времени генерации страницы тратится на перевод массивов в XML. Обход нескольких уровней массивов в PHP и сбор XML — очень ресурсоёмкая операция. Оптимизировали как могли — ничего не помогало. Время конвертации массивов в XML доходило до 150мс. И это всё для того, чтобы шаблонизатору данные «понравились». Это же хардкор. Проблему решили через написание расширения для PHP на С++. Он с этим справляется гораздо быстрее, но осадок остался плохой. На новом проекте (со сравнимым объёмом данных и размером шаблонов) вся страница (вместе с бизнесс-логикой), генерируется в 2-3раза быстрее чем мы тратили время преобразования массивов в XML на PHP.
                                                                                                • 0
                                                                                                  А проблема с классам решается отдельным шаблоном на класс, который можно переопределить и сделать apply-imports, а не if'ами
                                                                                                  • 0
                                                                                                    Приходится поддерживать проект с кучей XSLT-шаблонов. Замучились капитально. Потихоньку переписывается всё это на PHP-шаблоны и обретается счастье.
                                                                                                    • 0
                                                                                                      А мы вот, наоборот, радуемся. Все удобно и прозрачно. Видимо, надо просто уметь готовить.
                                                                                                      • 0
                                                                                                        Я поддержу BVadim, декларативные шаблонизаторы местами становятся крайне не удобными. Они гораздо хуже расширяются, не говоря о том, что работают медленно.
                                                                                                        И надо понимать, что в императивных вполне возможно применять одно-проходные алгоритмы (нет необходимости специально формировать данные для шаблонизатора).

                                                                                                        На счёт каши: она возможна НО при правильном проектировании её не будет. Не декларативный стиль даёт больше свободы и только вам решать, получится у вас каша или быстрая стройная система по генерации html/dom.

                                                                                                        ЗЫ а вообще у меня много претензий к xslt, и было много споров с сотрудниками yandex ;) единственный козырь xslt был в том что можно было разделить роли в разработке — программист, верстальщик. Но при использовании JSON и шаблнизации на клиенте как то этот довод уже мне кажется себя изжил.
                                                                                                        • 0
                                                                                                          Декларативный шаблон сложнее сломать и сложнее криво написать — это особенно хорошо проявляется в проекте на 50 человек, где обрасть знания проекта у каждого разработчика сильно ограничена. Да и в последнее время все больше шаблонизации делается декларативно — те же DOM-Based шаблоны в Kockout.js и Angular.js.

                                                                                                          У меня тоже когда-то было отвращение к декларативным шаблонам и XSLT — тут надо просто взглянуть с другой стороны на них, да и мозг на 45 градусов повернуть.

                                                                                                          Абзац философии
                                                                                                          В программировании как и в жизни важен баланс между полярными вещами для достижения прочности структуры. Сочетая декларативность и императивность мы получаем удобный и гибкий код. Если же мы делаем упор на что-либо одно, то как правило оргебаем, и получаем либо не удобно либо не гибко.

                                                                                                          Вот пример не удачного подхода — «императивный конфиг» (это даже сложно представить в мире где все конфиги в ini, YAML, JSON и XML).
                                                                                                          • 0
                                                                                                            Декларативный шаблон сложнее сломать и сложнее криво написать — это особенно хорошо проявляется в проекте на 50 человек, где обрасть знания проекта у каждого разработчика сильно ограничена.

                                                                                                            Не против, только может быть тут «плохому танцору»…
                                                                                                            И опять же:
                                                                                                            1. Если вам реально нужна производительность и вы ограничены в ресурсах то лучше императивный.
                                                                                                            2. Если фич заложенных в декларативный шаблон не хватает то он превращается в куда более жуткую лапшу (шаблоны в django это показывают).

                                                                                                            Абзац философии
                                                                                                            Это всё же больше дело вкуса… кто то гоняет на мотоцикле, а кто то на машине. Везде есть свои плюсы и минусы, и тут скорее дело вкуса и навыков.
                                                                                                  • 0
                                                                                                    Я написал небольшой шаблон XSLT, который позволяет компилить шаблон с наличием синтаксического сахара в обычный шаблон XSLT, и ваш пример можно записать так:
                                                                                                    <a href="{url}" x:if-attr="current" x:attr-class="current" x:val="name" xmlns:x="xslt-sugar"/>
                                                                                                    
                                                                                                    Хотя даже приведенный вами XSLT код не так уж и страшен, а вот отсутствие аналога <xsl:template> и осей навигации, это уже гораздо хуже, о чем автор статьи и говорит. Правда я не знаю, есть ли в Yate что-то подобное осям навигации, или это надо как-то через свои функции делать.
                                                                                      • 0
                                                                                        Императивный, декларативный… Вся эта чехарда с apply-templates — тупо завуалированные виртуальные методы/single dispatch/pattern-matching/называйте-как-хотите. Причем предельно загадочно приделанные.

                                                                                        Добавьте в императивный шаблонизатор диспетчеризацию и pattern-matching — и будет вам в разы лучше чем с XSLT. Добавьте еще higher order functions к этому — и будет вообще жир.
                                                                                        • +1
                                                                                          Правильно, добавляем patter-matching — получаем декларативный язык.
                                                                                          • 0
                                                                                            Чтобы сделать декларативный язык, надо добавить pattern-matching как-нибудь загадочно, ну типа как в XSLT. Если сделать прямо и понятно — ничего декларативного не получится. Ocaml — декларативный язык?
                                                                                            • 0
                                                                                              В XSLT это ещё и синтаксически уродски сделано.
                                                                                              • +1
                                                                                                XSLT синтаксически уродлив весь целиком.
                                                                                    • 0
                                                                                      Прежде чем говорить глупости прочитали бы исходники fest.
                                                                                      • 0
                                                                                        Что-то я не нашел там предикатов и apply-templates, покажите пример.
                                                                                      • 0
                                                                                        Fest — императивный шалонизатор, с конечно более продвинутыми возможностями, чем в handlebars, но семантика одинаковая.
                                                                                        • +1
                                                                                          Синтаксис был непростым решением.

                                                                                          Но я пока не знаю другого способа гарантировать XML на выходе, кроме как обработкой через sax парсер.
                                                                                          • 0
                                                                                            Мне не совсем понятно, зачем вы выбрали xml-синтаксис, если оперируете внутри шаблонизатора с JSON-данными? То есть, есть конечно аргументы про поддержку в редакторах и экранирование всех данных по-умолчанию. Но получается такая гремучая смесь, что мне лично это даже сложно читать, не говоря уже про написание и поддержку.
                                                                                            • 0
                                                                                              Я же написал чтобы гарантировать XML на выходе.

                                                                                              Если использовать fest в штатном режиме то невозможно получить невалидный XML на выходе.

                                                                                              Это гарантирует валидность разбора шаблона sax парсером, если шаблон на этапе компиляции разобран sax парсером это значит что во всех возможных исходах скомпилированная js функция выдасть валиный xml.
                                                                              • +3
                                                                                а можно вот эти места по подробнее?

                                                                                > реализации, как всегда, отличаются в IE и не в IE

                                                                                разумеется все процессоры разные, но почему ие вдруг ставится особняком? xslt придуман не мелкософтом, но реализован ими раньше всех.

                                                                                > игнорирование первого xsl:call-template

                                                                                не наблюдаю такого

                                                                                > и сложными предикатами

                                                                                например, какими?

                                                                                > а иногда — загрузка картинки до трансформации.

                                                                                иногда? какой картинки? откуда?

                                                                                > Хром требует отличного от других браузеров xsl:output.

                                                                                какого?

                                                                                больно уж они похожи на баги, с которыми было лень разбираться и свалили всё на «причуды браузера»

                                                                                из того, что я знаю, наиболее сильное отличие от остальных — в процессоре мозиллы и то не такие уж страшные, но про неё тут ни слова почему-то.

                                                                                > Самым популярным способом диагностирования проблем является комментирование кусков шаблона.

                                                                                это проблема также и любого препроцессора. будь то yate, bemhtml, stylus или любой другой. понять что происходит по нагенеренному коду может только тот, кто этот препроцессор написал (или хорошо его изучил). для остальных же, это чёрный ящик как и xslt.

                                                                                > в браузере же приходится сильно исхитряться со стандартными средствами, чтобы как-то нестандартно обработать строки

                                                                                очень спорный момент, должен ли этим заниматься шаблон. но таки да, за возможность запускать его в любом окружении (а не через виртуальную js-машину) приходится платить невозможностью расширить своими прибамбасами.

                                                                                > E4X на самом деле не очень удобный

                                                                                да ладно? одно только «root..descendant» чего стоит. или отсутствие «null pointer exception». по скорости — да, не нативно. но вы же яваскрипт не из-за скорости выбрали.

                                                                                далее, про тесты. я не нашёл в документации делает ли yate автоматическое экранирование данных (и если да, то решили ли вы проблему формирования json внутри html, где нужно двойное экранирование?). если нет экранирования, то тесты не корректны, синтаксис громоздкий, а XSS близко. от какого и до какого момента замерялась скорость (только трансформация или плюс парсинг данных, парсинг шаблона, формирование дома)? дело в том, что xslt позволяет сразу формировать поддерево целевого документа (а значит сериализация и как следствие экранирование не нужны вообще), а yate генерирует строку, которую потом ещё браузеру придётся парсить.

                                                                                кроме того в xslt есть интересная особенность — многопроходная трансформация, которая сильно помогает в случае, когда данные могут приходить в разных форматах — первым проходом нормализуем данные, а вторым формируем целевой документ.

                                                                                а в целом — не плохо, хоть один приличный json шаблонизатор. всё остальное либо императивное, либо как мусташ примитивное.
                                                                                • 0
                                                                                  тест-кейс для Оперы и картинок: stuff.androsov.net/opera_xsl_img_bug.html
                                                                                  • +3
                                                                                    1) то, что XSL впервые реализован в IE не отменяет той проблемы, что реализация во всех остальных браузерах от него отличается

                                                                                    2) возможно починили в свежих версиях оперы, но проблема точно есть в Opera 9.64, например, приходилось всегда объявлять <xsl:template name="null"/>, иначе самый первый <xsl:call-template> мог не отработать

                                                                                    3) например <xsl:template match="some[foo = bar][0]">

                                                                                    4) если в шаблоне есть <img src="..." onload="..." />, то эта картинка загрузится при чтении шаблона, ещё и onload может вызваться, проблема в том, что картинка грузится, а переменные в src не интерполируются, в итоге 404

                                                                                    5) все браузеры просят <xsl:output method="html"/>, а в хроме такой output работает не всегда и для него приходится генерить отделные шаблоны с <xsl:output method="xml"/>

                                                                                    6) такое мнение может пропасть, если почитать скомпилированный yate-шаблон, там всё достаточно понятно и логично, понятные имена функций, комментарии, у нас проблем с этим не возникало

                                                                                    7) очень спорный момент — это передавать с сервера дату сразу в 20 локалях и в индивидуальном формате для каждой локали, лучше передать timestamp и из него сделать правильный вывод при отрисовке view

                                                                                    8) у E4X не самая богатая документация и синтаксис не самый очевидный, он то «около-xpath», то js + он depricated + он только в SpiderMonkey + да, он медленный

                                                                                    9) да, yate автоматически экранирует данные, про JSON не совсем понял вопрос, но вроде он тоже экранируется

                                                                                    10) время трансформации — это время за которое из JSON с помощью скомпилированного шаблона получается строка с HTML, которая затем достаточно быстро вставляется в DOM с помощью innerHTML, script evaluation time для скомпилированного шаблона не учитывается, так как выполняется только один раз при загрузке шаблона и, например, профайлер оперы говорит, что уходит на это 2-3мс

                                                                                    11) в yate скоро появится генерация JSON, это не совсем многопроходная трансформация, но тоже весьма удобно, аналог exsl:node-set
                                                                                    • +2
                                                                                      1) то, что XSL впервые реализован в IE не отменяет той проблемы, что реализация во всех остальных браузерах от него отличается

                                                                                      в чём? или имеется ввиду javascript api? ну так спрятать различия в обёртку — не великий подвиг.

                                                                                      2) возможно починили в свежих версиях оперы, но проблема точно есть в Opera 9.64, например, приходилось всегда объявлять, иначе самый первый мог не отработать

                                                                                      ну вот, а говорите не развивается) пилят потихоньку. не так активно как модный «html5» к сожалению.

                                                                                      3) например

                                                                                      и что сложного в этом ни на что не матчащемся шаблоне?) для справки:
                                                                                      а) индексация в xpath начинается с единицы, а не с нуля
                                                                                      б) у элемента xsl:attribute нет никакого аттрибута select. поправьте ваш «пример» github.com/pasaran/yate/blob/master/examples/mailbox/mailbox.xsl#L452

                                                                                      4) если в шаблоне есть, то эта картинка загрузится при чтении шаблона, ещё и onload может вызваться, проблема в том, что картинка грузится, а переменные в src не интерполируются, в итоге 404

                                                                                      интересный баг, но при чём тут xslt? nin-jin.github.com/etc/opera-img-bug/

                                                                                      5) все браузеры просят, а в хроме такой output работает не всегда и для него приходится генерить отделные шаблоны с

                                                                                      в каких это случаях метод html не работает? и что значит не работает?

                                                                                      6) такое мнение может пропасть, если почитать скомпилированный yate-шаблон, там всё достаточно понятно и логично, понятные имена функций, комментарии, у нас проблем с этим не возникало

                                                                                      а где его взять простому смертному? впрочем, я не поленился и заморочился со скачиванием исправлением багов в вашем компиляторе, чтобы он не падал под виндой, исправлением глупых багов в шаблонах. nin-jin.github.com/etc/yate-vs-xslt/template.js — вот это вы называете «понятно и логично»? это типичный нагенеренный трешак с именами функций вида t42 и переменными вида v13.

                                                                                      7) очень спорный момент — это передавать с сервера дату сразу в 20 локалях и в индивидуальном формате для каждой локали, лучше передать timestamp и из него сделать правильный вывод при отрисовке view

                                                                                      а зачем передавать сразу 20 локалей, когда нужна всего одна? и тогда уж не timestamp а в iso, который понятен человеку. но тут ещё ладно, дата — вещь атомарная — её куда угодно можно присунуть. а вот формирование урлов с помощью яваскрипта в шаблонизаторе — это ахтунг. github.com/pasaran/yate/blob/master/examples/mailbox/mailbox.yate#L425
                                                                                      эти урлы должны либо приходить с данными, либо для них должны быть отдельные шаблоны (с матчингом и плейсхолдерами, а не ифами и конкатенацией). в конце концов, на кой чёрт данные для экшенов фигачить в урл? они либо в теле сообщения должны быть, либо в uri ресурса (в данном случае сообщения), который и должен приходить с данными.

                                                                                      8) у E4X не самая богатая документация и синтаксис не самый очевидный, он то «около-xpath», то js + он depricated + он только в SpiderMonkey + да, он медленный

                                                                                      уж кто бы говорил про документацию) ну да, не взлетел. но штука всё же классная.

                                                                                      9) да, yate автоматически экранирует данные, про JSON не совсем понял вопрос, но вроде он тоже экранируется

                                                                                      про json вопрос был в том, чтобы можно было формировать ваш любимый onclick=«return {...}» без необходимости вручную экранировать каждое значение. аналогично с урлами и прочими языками в языке.

                                                                                      10) время трансформации — это время за которое из JSON с помощью скомпилированного шаблона получается строка с HTML, которая затем достаточно быстро вставляется в DOM с помощью innerHTML, script evaluation time для скомпилированного шаблона не учитывается, так как выполняется только один раз при загрузке шаблона и, например, профайлер оперы говорит, что уходит на это 2-3мс

                                                                                      а я вот тут потестил на вашем «примере» и у меня графики получились не такие классные. nin-jin.github.com/etc/yate-vs-xslt/ что я делаю не так?
                                                                                      по моим данным скорость примерно равна с перевесом в сторону xslt во всех браузерах, кроме хрома. yate разворачивает 24кб шаблон в 42кб и плюс требует 24кб рантайма. xslt шаблон занимает 25кб и парсится за те же единицы миллисекунд. при этом если сделать рефакторинг шаблонов и серверной выдачи (упростить структуру и избавиться от сложной логики) — можно ещё сильнее ускорить и ужать в размере. но это не так интересно как изобретать велосипед ;-) кстати, вопреки расхожему мнению, данные в json формате оказались больше по объёму, чем те же данные в xml.
                                                                                    • 0
                                                                                      Автоматический эскейпинг, конечно, есть. Без него можно разве что hello world писать.
                                                                                      Про формирование json — это в ближайших планах. Будет и преобразование json в json, и временные деревья, и многопроходность.
                                                                                    • +1
                                                                                      Прошу не бить, но у меня возникла ассоциация с XAML и QML. Возможно, из-за отдаленной схожести синтаксиса.
                                                                                      • –2
                                                                                        Название не очень удачное. Есть проект yate который занимается телефонией.
                                                                                        • 0
                                                                                          Я сильно недолюбливаю XML формат. Длинные конструкции, всегда много буков… Читается тяжело. Надо повторять имя тега при закрытии. При создании нового формата надо думать, что сделать текстовой нодой, а что атрибутами.

                                                                                          А JSON лаконичный, краткий. Разве что есть некоторые мудрости с экранировкой, но с этим наследием JavaScript я могу смириться.

                                                                                          Конечно понятно, что у XML длинная история, стандартизировано куча подмножеств, куча библиотек. Есть стандартные средства преобразований, валидации, обработки и т.п. А в JSON это пока все разрозненно и не общепринято.

                                                                                          Но если мне надо хранить или обмениваться структурами данных, я практически всегда предпочту JSON. В том числе и в передаче данных для шаблонизаторов. Я буду рад, если со временем JSON хорошо потеснит XML.
                                                                                          • +1
                                                                                            Очень хорошо, когда видно имя закрытого тега, а не обезличенные }}}} или )))). Я работал руками и с XML данными, и с JSON, так вот с JSON было больше проблем, и ошибки искать приходилось дольше. XML конечно тоже не подарок, и я был бы рад, если бы в будущем предложили что-то отличное и от XML, и от JSON, более человечное, к примеру как Markdown по сравнению с HTML.
                                                                                        • –2
                                                                                          А как же doT?
                                                                                          • +4
                                                                                            Зачем Яндексу ещё один декларативный xslt-подобный шаблонизатор, когда уже есть BEMHTML?
                                                                                            • 0
                                                                                              Два вопроса:
                                                                                              — Насколько реально написать компилятор Yate -> PHP
                                                                                              — Почему было-бы не написать XSLT -> JavaScript компилятор, вместо создания нового языка шаблонов?
                                                                                              В этом случае не пришлось бы переписывать существующие XSLT шаблоны на Yate.
                                                                                              • 0
                                                                                                XSLT -> JavaScript компилятор
                                                                                                XSLT + xsl2yate -> Yate -> JavaScript
                                                                                                • 0
                                                                                                  1. Написать компилятор в php (и другие языки) реально.
                                                                                                  Собственно, изначально была такая цель. Но пока не до конца все готово для этого.
                                                                                                  Кодогенерация описана в отдельном шаблоне (это для js).
                                                                                                  Пока что там не все, но в будущем можно будет написать php.tmpl и генерить php (perl, python, ...).

                                                                                                  2. xslt нас устраивает концептуально, но есть разные нюансы. Громоздкий xml-based синтаксис. Невозможность расширения и т.д.
                                                                                                  • 0
                                                                                                    Почему это невозможно расширять? В XML как раз заложена такая возможность, через xmlns, и последующие обработчики. Я вот сделал небольшой шаблон, упрощающий синтаксис XSLT, на самом же XSLT, годится для прекомпиляции шаблонов, как и в Yate.

                                                                                                    На первый взгляд в Yate языковые конструкции сливаются с текстом, в этом отношении XSLT лучше, он выглядит как и получаемый с его помощью HTML/XML, хотя конечно нужно на практике смотреть, может я и не прав, и шаблоны Yate на самом деле удобнее, но! Применение Yate только на клиенте сильно уменьшает возможности использования этого шаблонизатора, большинство сайтов необходимо шаблонизировать на сервере, изучать сложный шаблонизатор только ради части своих проектов не хотелось бы.