От автора: в первую очередь производительность браузера повышается за счет кэширования CSS. Проверьте, что ваш сервер отправляет заголовки, которые говорят браузеру хранить CSS файлы определенное время. Это наилучший подход, которым пользуются на большинстве, если не на всех сайтах.
Кэширование очень тесно связано с браузером, и в итоге легче его отключить. Задайте в настройках браузера хранить кэш CSS один год (что не редкость). И вдруг вам понадобилось изменить стили. В таком случае вам нужно подумать, как очистить кэш и заставить браузер перезагрузить CSS. Ниже представлены несколько вариантов по решению этой задачи.
CSS необходимо кэшировать, это очень важно…
Просто посмотрим на то, как выглядят заголовки для кэширования CSS файлов:
Нам нужны Cache-Control и Expires. Я не эксперт в области конфигурации серверов, обычно я смотрю в H5BP конфиги. Но в нашем случае есть классический способ через Apache/HTAccess:
1 2 3 4 5 6 7 8 9 |
<FilesMatch "\.(ico|pdf|flv|jpg|jpeg|png|gif|js|css|swf)(\.gz)?$"> Header set Expires "Thu, 15 Apr 2020 20:00:00 GMT" </FilesMatch> <IfModulemod_expires.c> ExpiresActive on ExpiresByType text/css "access plus 1 year" ExpiresByType application/javascript "access plus 1 year" </IfModule> |
Запросы
Сейчас браузеры видят URL с какими-либо запросами, как отдельные файлы и просто обновляют их на свежие копии. Большинство CDN поддерживают такую функцию и рекомендуют ее.
1 |
<link rel="stylesheet" href="style.css?v=3.4.1"> |
Что-то не так? Измените на это:
1 |
<link rel="stylesheet" href="style.css?v=3.4.2"> |
Можно облегчить этот процесс, установив переменную на сервере, чтобы потом использовать ее везде, где необходимо. Тогда бы при любом изменении файл кэша разбивался бы на множество отдельных файлов.
1 2 |
<?php $cssVersion="3.4.2";?> <link rel="stylesheet" href="global.css?v=<?php echo $cssVersion; ?>"> |
Скорее всего, вы даже могли бы использовать семантическое версионирование, а также можно задать константы.
Изменение имени файла
Запросы не всегда срабатывают. Некоторые браузеры не различают разные строки запросов, как разные файлы. А некоторое ПО (Squid) вообще не кэширует файлы по строковым запросам. Steve Souders в своей статье рассказывает, почему не стоит использовать строковые запросы. Похожая техника применяется с изменением имени файла. Как в HTML ниже:
1 |
<link rel="stylesheet" href="style.232124.css"> |
Необходимо программно изменить имя файла, а не просто вбить готовое. Таким образом, файл на самом деле не существует вообще, вам придется написать пару строк кода, чтобы попасть к нужному файлу. Совсем недавно Jeremy Keith открыл эту технику.
1 2 |
RewriteCond %{REQUEST_FILENAME} !-f RewriteRule^(.+).(d+).(js|css)$ $1.$3 [L] |
Сервер будет игнорировать цифры в именах файлов CSS и JavaScript, однако браузер все же будет считать названия файлами и будет пытаться обновить код. Jeremy Keith пользуется Twig и применяет следующий шаблон:
1 2 |
{% set cssupdate = '20150310' %} <link rel="stylesheet" href="/css/main.{{ cssupdate }}.css"> |
Уверен, что вы можете представить похожий код на любом backend языке (типа ASP). Можно потренироваться с написанием данного скрипта для обновления переменной.
Отключение кэширование основано на обновлении даты
Во время поиска в интернете по поводу отключения кэширования вы наткнетесь на кучу советов, вам будут рекомендовать использовать сервер для проверки последнего обновления кэшированного файла и создать «номер» отключения кэша (номер означает что угодно, что вы можете изменить для обновления кэша).
1 2 3 4 5 6 |
functionautoversion($url){ $path =pathinfo($url); $ver='.'.filemtime($_SERVER['DOCUMENT_ROOT'].$url).'.'; return $path['dirname'].'/'.str_replace('.', $ver, $path['basename']); } <link href="<?phpautoversion('/path/to/theme.css'); ?>" rel="stylesheet"> |
Вообще, я не слишком в этом хорош. Мне кажется, что каждый раз спрашивать сервер при просмотре страницы будет крайне опасно. Раньше я вообще искал фото на сервере по его размерам! Будьте осторожны, в общем.
ETag’и
Возможно ETag’и покажутся хорошей идеей, так как большинство из них это информация о том, имеются ли уже у браузера копии файлов. Но большинство советчиков в интернете говорят: «отключайте ETag заголовки». Yahoo говорит:
«Вся проблема с ETag’ами в том, что они создаются с помощью атрибутов, которые делают их уникальными для каждого сервера. ETag’и не совпадут, если браузер получил компонент от одного сервера, и тот пытается проверить компонент на другом сервере. Общая проблема сайтов, построенных на кластерных серверах.»
Другая проблема в том, что они просто не эффективны при кэшировании. Для проверки ETag’ов все еще нужно делать сетевые запросы. Это не просто загрузка файлов, которая уменьшает производительность, а также различные задержки на стороне сервера при обработке запросов.
И снова я не эксперт в этой тематике, но рекомендуется отключить их в Apache:
1 2 3 4 |
<IfModulemod_headers.c> Header unset ETag </IfModule> FileETagNone |
Дело для фреймворков
Rails файлопровод
Я немного поработал с Rails файлопроводом и Sprockets. Если вы спросите меня, что это, я отвечу, что это фреймворки мечты. Я указал ссылку в шаблоне:
1 |
<%= stylesheet_link_tag "about/about" %> |
Которая генерирует HTML:
1 |
<link href="//assets.codepen.io/assets/about/about-7ca9d3db0013f3ea9ba05b9dcda5ede0.css" media="screen" rel="stylesheet" type="text/css" /> |
Данное число для отключения кэширования меняется только в том случае, если что-то меняется в файле, так что можно вообще отключить кэш на файлы. В добавку к этому, есть похожий метод для изображений и JavaScript файлов.
WordPress
Если вы применяете кэширование страниц в WordPress, типа W3 TotalCache или еще что-то, то вам можно не беспокоиться, что filemtime нагрузит сервер. Gilbert Pellegrom написал статью о технике отключения кэша на WordPress, в ней он использовал этот код:
1 2 3 |
wp_register_style('screen', get_template_directory_uri() . '/style.css', array(), filemtime(get_template_directory() . '/style.css')); wp_enqueue_style('screen'); // Пример выходного файла: /style.css?ver=1384432580 |
Плагин Busted! делает то же самое, только автоматически.
CodeKit
В CodeKit нету встроенного метода изменения имени файлов, но есть способ написать Shell скрипт.
У Michael Russell есть статья о том, как вставить временные отметки в самих себя, которые, как я уверен, можно модифицировать, чтобы изменить имя файла.
Сборки
Во всех популярных таск-раннерах есть плагин для изменения имени файла. У Sufian Rhazi есть статья о том, как делать это через Node.js.
Grunt
Gulp
Broccoli
С помощью препроцессоров
Во время линковки различных ресурсов (к примеру, изображение из LESS файла) можно подключить препроцессор. У Ben Nadel есть статья.
Асинхронная загрузка CSS
Критический CSS становится все более популярным. Есть причины и кроме асинхронной загрузки, это отложить загрузку CSS (можно встроить CSS в тело страницы). Если вы загружаете CSS с помощью loadCSS (или вставляете тег ссылки), вам нужно обновить запрашиваемое в JavaScript имя файла. Иначе, изменив имя файла, вы не обновите CSS код.
Автор: Chris Coyier
Источник: //css-tricks.com/
Редакция: Команда webformyself.