Программист
0,0
рейтинг
12 сентября 2013 в 07:12

Разработка → Плагин для Smarty — Combine из песочницы

PHP*
Плагин позволяет собрать несколько CSS или Javascript файлов воедино.

Я согласен, что подобных программных решений очень много, например Minify, YUI Compressor или конкантенатор из Pagespeed service от Google. Но для шаблонизатора Smarty мне подобного не попадалось, и я решил написать свое и попроще.
Combine
Плагин работает довольно просто: когда один из включаемых файлов изменяется, он создает новый выходной файл и возвращает к нему путь.

Плагин позволяет решить 2 проблемы — модульность и контроль за обновлением файлов на стороне клиента.
Проблема модульности заключается в том, что для относительно сложных проектов приходится подключать большое число разных CSS и JS файлов. Все это приводит к дополнительным запросам к серверу. Да, front-end сервера с этим прекрасно справляются, но зачем делать 10 запросов, когда можно сделать один? А если хочется сократить это число привычными методами, приходится использовать различные дополнительные решения или собирать файл вручную. Лично для меня, файл после первой 1000 строк превращается в адское месиво, поэтому я стараюсь разделять код на несколько модулей или фрагментов.
Проблема контроля за обновлением ресурсов на стороне клиента не менее важна. Наверняка многие сталкивались со старой версией CSS или JS файла у какого-нибудь клиента, которая вызывала ошибку из-за изменившейся верстки или API на back-end'e. И тут подводных камней действительно много, т.к. кэширование зависит и от браузера, и от прокси, а может еще и от провайдера зависеть (редко, но некоторые держат прозрачный прокси). Единственный стопроцентно рабочий способ — изменить имя файла. Остальные могут не сработать.

У плагина есть список из трех входных параметров:
  1. input, представляющий собой простой массив, содержащий в себе список путей к склеиваемым файлам;
  2. output, представляющий собой путь к выходному файлу;
  3. age, время в секундах между проверками на изменение одного из включаемых файлов. Этот параметр можно опустить, по умолчанию он равен 3600 секундам.

Расскажу зачем нужен age — операции ввода-вывода одни из самых проблемных на сегодняшний день. Несмотря на появление SSD-накопителей, время доступа к файлу все же присутствует и, если много обращений к файлам, в приложении могут возникать проблемы производительности. Сейчас это все хорошо кэшируется, но зачем же обращаться в кэш, когда этого можно не делать? Каждый разработчик сам вправе регулировать частоту проверки на актуальность файлов, но я бы не рекомендовал ставить меньше 3 секунд, так как это почти бессмысленно. В своих проектах я передаю этот параметр в виде переменной, которая зависит от режима работы сайта. Если сайт находится в режиме отладки, там 5 секунд, в противном случае — 3600.

Исходный код

Код доступен на GitHub.

Образец подключения в шаблоне

В Smarty 3 есть возможность создания массива на лету, поэтому код приведен с учетом этой возможности. Для Smarty 2 массив нужно передавать через отдельную переменную.

<script type="text/javascript"
src="/{combine input=array('/js/core.js','/js/slideviewer.js') output='/js/big.js' age='30'}" >



При работе плагина есть несколько ньюансов. Путь к файлам должен идти от document_root, а папка с выходным файлом должна разрешать запись и создание новых файлов. Нельзя одновременно объединять файлы CSS и JS.

Плагин протестирован с Smarty 2 и Smarty 3. Сейчас используется в проекте с посещаемостью около 4000 человек в сутки. Проблем не наблюдал. Буду благодарен за багрепорты и предложения по развитию.
Philipp Tkachev @zoonman
карма
9,0
рейтинг 0,0
Программист
Реклама помогает поддерживать и развивать наши сервисы

Подробнее
Реклама

Самое читаемое Разработка

Комментарии (10)

  • 0
    Генерация происходит в момент компиляции Smarty-шаблона или сначала генерируется специальна ссылка, которая ведет к скрипту, который при первом обращении сгенерирует соответствующий упакованный JS файл?

    + Забыли про CDN и уже закешированные в браузере пользователя библиотеки.
    • 0
      Генерация ссылки происходит в момент компиляции шаблона.
  • +4
    Очередной велосипед?

    function sfc_get_file_ext($filename) {
        $rm=explode(".", $filename);
        if(is_array($rm)) {
            if (isset($rm[count($rm)-1]))	{
                return $rm[count($rm)-1];
           }
        }
       return '';
    }
    


    Так по моему проще:

    function sfc_get_file_ext($filename) {
        return pathinfo($filename, PATHINFO_EXTENSION);
    }
    
    • 0
      Вы безусловно правы. Обновлю код обязательно.
      • 0
        Можно и через (но вернет расширение с точкой):
        strrchr($filename, '.')

  • 0
    И зачем постоянно проверять на function_exists?

    if (!function_exists('sfc_get_file_ext')) {
    		function sfc_get_file_ext($filename) {
    


    Не легче ли было объявить эти фукнции наравне с самой функцией плагина smarty_function_combine?
    • 0
      Может быть привычка Wordpress-разработчика? :)

      С праздником.
  • +1
    Думаю, что в качестве развития, было бы неплохо добавить мимими минимизатор результатов комбинирования — тот же Minify.
    • 0
      А также параметр development, который бы комбинировал скрипты / цсс только на продакшене, подставляя оригиналы при отладке.
      • 0
        Отличная идея, о которой я всерьез задумывался. Полагаю, что со временем введу подобный функционал.

Только зарегистрированные пользователи могут оставлять комментарии. Войдите, пожалуйста.