Как стать автором
Обновить

Комментарии 22

Внешний CSS не блокирует дальнейшую обработки страницы, в отличие от JS.

Но блокирует же.
By default, CSS is treated as a render blocking resource.
Да, это вопрос:

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

Вывод: «блокировка» в контексте CSS, что на самом деле означает не блокировка, а «приостановка вывода страницы», не одно и тоже, что «блокировка дальнейшей обработки» в контексте JS.
«Вот такая загагулина.»
Но что подразумевается под «дальнейшей обработкой»? Построение rendering tree, отрисовка?
CSS блокирует вывод на экран, синхронный JS тоже.

Отсюда появился другой вопрос, в чем разница между «приостановкой вывода страницы» и «блокировкой дальнейшей обработки»?
Вот тут человек пишет:
Давайте сначала рассмотрим, в чем заключается проблема с загрузкой скриптов. Все заключается в том, что браузер не может сказать, что находится внутри скрипта, не загрузив его полностью. Скрипт может содержать вызовы document.write(), которые изменяют DOM-дерево, или вообще location.href, что отправит пользователя на другую страницу. В последнем случае все компоненты, загруженные на предыдущей странице, могут оказаться ненужными. Чтобы предотвратить загрузки, которые могут оказаться лишними, браузеры сначала загружают, затем анализируют и исполняют каждый скрипт перед тем, как переходить к следующему файлу в очереди на загрузку. В результате каждый вызов скрипта на вашей странице блокирует процесс загрузки и оказывает негативное влияние на скорость загрузки.

В отличие от CSS, т.е. от приостановки вывода страницы.
Давайте проверим это утверждение на практике:

  1. Заходим сюда
  2. Смотрим html, убеждаемся что нет async
    спойлер
          <script type="text/javascript" src="//habracdn.net/habr/javascripts/1444315133/_parts/posts.js"></script>
      <script type="text/javascript" src="//habracdn.net/habr/javascripts/1444315133/libs/jquery.form.js"></script>
      <script type="text/javascript" src="//habracdn.net/habr/javascripts/1444315133/libs/highlight.8.8.0.pack.js
    "></script>
      <script type="text/javascript" src="//habracdn.net/habr/javascripts/1444315133/hubs/all.js"></script>
      <script type="text/javascript" src="//habracdn.net/habr/javascripts/1444315133/posts/all.js"></script>
    


    Судя по утверждению, скрипты должны загрузиться последовательно.
  3. Открываем Chrome Dev Tools, отключаем кэш и
    видим


    что запросы начались почти что одновременно.
Все верно, но следуя этому мануалу, нас интересует синий цвет легенды (не ожидание первоначального ответа, а время загрузки контента):
image
Точнее, не время ожидания (зеленая шкала), а время начала загрузки контента (синяя). Если посмотреть на второе изображение Вашего поста, там видно, что синие шкалы легенды не пересекаются.
Нет, нас интересует когда запросы был создан (Request sent). Впрочем, это неважно, на моем скриншоте видно что синие полоски тоже не последовательны и если присмотреться, то они все же пересекаются 2 и 4 запрос.
В статье на которую вы указали, говорится именно о том, что пока скрипт не отработает полностью, запрос для следующего скрипта даже не будет создан (читай не появится зеленая полоска).

Второй момент, статья эта очень старая и она отражает состояние браузеров до IE8, во всех современных браузерах есть такая вещь как pre-loader, который решает проеблему описанную в вашей статье.

Ну и третий момент, если уже быть совсем последовательными, то в вашей статье, так же говорится что в старых FF, загрука стилей тоже была последовательной, именно загрузка а не обработка.
Верно, нас интересует даже не время начальной загрузки, а время поступления запроса «Request sent», но тогда благодаря механизму pre-loader, который еще в 2008 году реализован на Internet Explorer, WebKit and Mozilla, как указано в Вашей статье имеем:
When the browser is blocked on a script, a second lightweight parser scans the rest of the markup looking for other resources e.g. stylesheets, scripts, images etc., that also need to be retrieved.

The pre-loader then starts retrieving these resources in the background with the aim that by the time the main HTML parser reaches them they may have already been downloaded and so reduce blocking later in the page.

Т.е. прелоадер в фоновом режиме уже подгрузит остальные компоненты сайта, в т.ч. и скрипты. Получается, что ориентироваться на начало Request sent нет смысла и остается только панель Timeline, как Вы правильно меня поправили, с временем начала выполнения каждого из скриптов.
И вопрос – в чем принципиальное отличие, остается открытым.
Да, все верно. Я и не говорил что CSS или JS блокируют загрузку, конечно нет, если вы не используете IE7-.
Я привел панель Network для того, чтобы опровергнуть тезис, что JS блокирует загрузку последующих скриптов, как говорилось в статье на которую вы сослались.

Более того, CSS блокирует не только рендеринг страницы, но и выполнение синхронного JS если этот JS расположен ниже CSS.
JavaScript execution blocks on CSSOM.


Итого:
  • CSS блокирует выполнение синхронного JS
  • Раз CSS блокирует выполнение синхронного JS, то значит он блокирует DOM construction косвенно
  • CSS блокирует рендеринг страницы даже если на этой странице нет JS
  • В современных браузерах загрузка не блокируется ничем


И вовращаясь к первому комментарию: я не понял что хотел сказать автор статьи этой фразой:
Внешний CSS не блокирует дальнейшую обработки страницы, в отличие от JS.
Сделал специально с эмуляцией GRPS чтобы было более убедительно.
И на панели Timeline, выбрав «Profile JS» проще проследить по шкале времени последовательность загрузки скриптов (IMHO), как тут:

image
Абсолютно нет, на этой панели вы видите не последовательность загрузки, а последовательность выполнения (scripting). Да скрипты выполняются последовательно, это известно, но и CSS обрабатывается (построение CSSOM) последовательно.
Да, именно выполнения, а не загрузки.
Если во внешнем CSS шрифты, то браузер будет ждать их для отрисовки, вы про это?
Нет, я про то что пока CSS не загрузится, рендеринг не начнется.
Со шрифтами немного другая логика, IE, например, не дожидается загрузки шрифтов и рендерит сразу, и делает ререндер когда шрифт подгрузился.
Chrome и FF ждут до 3 секунд и рендерят. Если шрифт не успел загрзиться в 3 секунды, то сделают ререндер когда он загрузится.
Прекрасная статья, спасибо за перевод!
Должен быть только один удаленный JS-файл и один удаленный CSS-файл.

Бытует мнение, что желательно размещать, к примеру, такие вещи как jQuery и Bootstrap компоненты на удаленных CDN серверах для ускорения загрузки страниц сайта.

В этом случае оптимальнее их разместить на CDN или перетащить к себе на сервер?
CDN
Наверное, оптимальным решением будет грузить их с CDN, но если они какое-то время не загружаются, то дергать копии, хранящиеся на своем сервере. Помню, несколько лет назад был случай по работе, когда CDN умер, jQuery с него загрузиться не могла, в итоге все скрипты на сайте стали неработоспособны.

Вероятность такого, конечно, очень мала, но все же есть. Если упадет ваш сервер, то тут все понятно, сайт будет недоступен. Но если качать библиотеки исключительно с CDN, не давая альтернативы, то к маленькой вероятности падения сервера добавляется маленькая вероятность падения CDN и вместе они уже образуют чуть большую вероятность потерь.
Спасибо! Наличие резервного варианта лишним не будет.
фраза «Если вы используете Rails, то это сделано заранее. » не передает суть оригинала, там может быть что-то про средства сделать конкатенацию встроенными утилитами Rails?
Ну и «JavaScript не бесплатен, %username%»
Зарегистрируйтесь на Хабре , чтобы оставить комментарий