config.assets.compile = true в производстве Rails, почему бы и нет?

185

Приложение Rails по умолчанию, установленное пользователем, rails newнаходится config.assets.compile = falseв производстве.

И обычный способ сделать это - запустить rake assets:precompileперед развертыванием приложения, чтобы убедиться, что все активы конвейера активов скомпилированы.

Так что же произойдет, если я начну config.assets.compile = trueпроизводство?

Мне precompileбольше не нужно бежать . Я верю, что произойдет, когда первый раз запрашивается актив, он будет скомпилирован. Это будет удар по производительности в первый раз (и это означает, что для этого обычно требуется среда выполнения js). Но кроме этих недостатков, после того, как актив был лениво скомпилирован, я думаю , что весь последующий доступ к этому активу не будет иметь никакого снижения производительности, производительность приложения будет точно такой же, как с предварительно скомпилированными активами после этой первоначальной ленивой компиляции первого удара. Это правда?

Я что-то пропустил? Какие-либо другие причины, чтобы не запускать config.assets.compile = trueв производство? Если у меня есть среда выполнения JS в процессе производства и я готов взять компромисс с ухудшением производительности при первом доступе к активу в обмен на отсутствие запуска precompile, имеет ли это смысл?

jrochkind
источник
1
Предупреждение, более старые версии звездочек содержат ошибку, и если config.assets.compile настроен на true, существует риск уязвимости обхода каталога ( blog.heroku.com/rails-asset-pipeline-vulnerability )
Mauro
Именно так должен работать Stackoverflow. Хорошо написанный вопрос и хорошо написанный ответ. Я люблю вас обоих op и @ richard-hulse.
Schmijos

Ответы:

259

Я написал эту часть руководства.

Вы определенно не хотите жить в процессе компиляции.

Когда у вас есть компиляция, вот что происходит:

Каждый запрос файла в / assets передается в Sprockets. При первом запросе для каждого актива он компилируется и кэшируется во все, что Rails использует для кэширования (обычно файловая система).

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

Это все в папке активов и в любых папках vendor / assets, используемых плагинами.

Это много накладных расходов, так как, если честно, код не оптимизирован по скорости.

Это повлияет на скорость передачи активов клиенту и негативно скажется на времени загрузки страницы вашего сайта.

Сравните со значением по умолчанию:

Когда ресурсы предварительно скомпилированы и компиляция выключена, ресурсы скомпилированы и сняты с отпечатком пальца public/assets. Sprockets возвращает таблицу сопоставления имен файлов с простым отпечатком в Rails, а Rails записывает это в файловую систему. Файл манифеста (YML в Rails 3 или JSON со случайным именем в Rails 4) загружается в Memory при помощи Rails при запуске и кэшируется для использования вспомогательными методами ресурсов.

Это делает создание страниц с правильными отпечатками очень быстрыми, а сами файлы обрабатываются с помощью веб-сервера из файловой системы. Оба значительно быстрее, чем живая компиляция.

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

Это позволяет клиенту получать активы как можно быстрее и с наименьшим возможным размером, ускоряя отображение страниц на стороне клиента и сокращая (с заголовком в далеком будущем) запросы.

Так что, если вы живете, это:

  1. Очень медленно
  2. Не хватает сжатия
  3. Будет влиять на время рендеринга страниц

Против

  1. Быстро настолько, насколько это возможно
  2. Сжатый
  3. Удалите сжатие, подслушанное с сервера (опционально).
  4. Минимизируйте время рендеринга страниц.

Изменить: (Ответ, чтобы прокомментировать комментарий)

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

Кроме того, кто-то должен будет заплатить цену медленной доставки активов в течение неизвестного периода времени, пока все активы не будут собраны и введены в действие.

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

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

[Редактировать, июнь 2015 г.] Если вы читаете это, потому что ищете решение для медленного времени компиляции во время развертывания, то вы можете рассмотреть возможность предварительной компиляции ресурсов локально. Информация об этом находится в руководстве по конвейеру активов . Это позволяет вам прекомпилировать локально только при наличии изменений, зафиксировать их, а затем выполнить быстрое развертывание без стадии прекомпиляции.

Ричард Халс
источник
1
Спасибо, я принял ваш ответ. Но теперь мой вопрос, ладно, сейчас он этого не делает, но возможно вы думаете, что Asset Pipeline может иметь функцию, которая лениво компилируется при первом запросе, делая это в точности как прекомпиляция, включая запись в ./public и обновление манифест отпечатков пальцев?
Джрочкинд
Смотри выше. Это проблема, потому что Capistrano не работает для вас?
Ричард Халс
Я не использую Capistrano. Мне не нужно было раньше, сложность не стоила того. Возможно, трубопровод активов - это солома, которая ломает верблюдов и требует этого. По вашему мнению, невозможно управлять развертыванием Rails с помощью конвейера активов без Capistrano или подобного? Обидно, для простых установок это было не большой проблемой, чтобы сделать это вручную.
jrochkind
Вам действительно нужен Capistrano для Rails 3.1. Ресурсы компилируются в новом общедоступном каталоге, пока ваше старое приложение еще работает. Когда компиляция завершена, новая версия имеет символическую ссылку и сервер автоматически перезагружается.
Ричард Халс
«Чтобы получить максимальную выгоду от конвейера и снятия отпечатков пальцев, вам необходимо установить заголовки на будущее на своем веб-сервере и включить сжатие gzip для файлов js и css». - Не могли бы вы предоставить некоторые инструкции или ссылки, как это сделать? этот?
Исаак Бетеш
7

Чтобы иметь меньше накладных расходов с предварительной компиляцией.

Precompile everything initially with these settings in production.rb
# Precompile *all* assets, except those that start with underscore
config.assets.precompile << /(^[^_\/]|\/[^_])[^\/]*$/

затем вы можете просто использовать изображения и таблицы стилей, например, "/assets/stylesheet.css" в * .html.erb или "/assets/web.png".

dbKooper
источник
6

Для тех, кто использует Heroku:

Если вы развертываете в Herkou, он будет выполнять прекомпиляцию автоматически для вас во время развертывания, если скомпилированные ресурсы не включены (т.е. public/assetsне зафиксированы), поэтому нет необходимости config.assets.compile = trueили фиксировать предварительно скомпилированные активы.

Документы Heroku здесь . Для удаления нагрузки на ресурс dyno рекомендуется CDN .

Уильям Денисс
источник
1

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

Фредерик Чунг
источник
Хм, я думал, что при precompile=trueэтом скомпилированные ресурсы будут записаны в файловую систему. Ты уверен? Позвольте мне проверить ...
jrochkind
1
Бах, я думаю, что вы правы - они записаны в файловую систему, но похоже, что tmp/cacheвместо того public/assets, чтобы веб-сервер мог видеть, они все равно будут обслуживаться приложением rails, а не веб-сервер. л. это правильно, вы думаете?
jrochkind
Верный. Не так быстро, как если бы веб-сервер подобрал их прямо сейчас. Может быть, не имеет значения, если вы поместите облачный фронт, похожий на cdn, перед вашим приложением
Фредерик Ченг,
1

Устанавливать config.asset.compile = false

Добавить в свой Gemfile

group :assets do gem 'turbo-sprockets-rails3' end

Установите пакет

Бегать rake assets:precompile

Затем запустите свой сервер

Мохаммед Салим
источник
Насколько я установил config.asset.compile = true in production.rbфайл, потому что там не добавлен механизм предварительного завершения. Из-за этого каждый раз, когда мы запускаем сервер, загрузка страницы занимает слишком много времени (когда запрос попадает как в обработку запроса, так и в компиляцию ресурсов). Теперь я включил turbo-sprockets-rails3Gemfile и запустил команду, которая rake assets:precompileпредварительно компилирует ресурсы. Теперь я устанавливаю config.asset.compile = false in production.rbи запускаю сервер, загрузка страницы происходит без задержек. (Только обработка запроса без компиляции активов)
Мохаммед Салим
2
Стоит сказать, что turbo-sprockets-rails3это необходимо только на Ruby 3
Andre Figueiredo
0

Из официального руководства :

По первому запросу ресурсы компилируются и кэшируются, как описано выше в разработке, а имена манифестов, используемые в помощниках, изменяются, чтобы включить хэш MD5.

Sprockets также устанавливает HTTP-заголовок Cache-Control на max-age = 31536000. Это сигнализирует всем кэшам между вашим сервером и браузером клиента, что этот контент (обслуживаемый файл) может быть кэширован в течение 1 года. Результатом этого является уменьшение количества запросов на этот ресурс с вашего сервера; актив имеет хорошие шансы быть в кеше локального браузера или в некотором промежуточном кеше.

Этот режим использует больше памяти, работает хуже, чем по умолчанию, и не рекомендуется.

Кроме того, этап прекомпиляции не является проблемой, если вы используете Capistrano для своих развертываний. Это позаботится об этом для вас. Ты просто бежишь

cap deploy

или (в зависимости от вашей настройки)

cap production deploy

и все готово Если вы все еще не используете его, я настоятельно рекомендую проверить это.

Серхио Туленцев
источник
Так вы думаете, что язык из официального гида со мной согласен? Я видел это руководство, я не совсем уверен, если это означает, что я предлагаю выше, что вы думаете? Это мой вопрос.
Джрочкинд
Да, вы говорите в основном то же самое. Я предлагаю вам не включать живую компиляцию.
Серхио Туленцев