Включить активы только в том случае, если они существуют - программирование
Подтвердить что ты не робот

Включить активы только в том случае, если они существуют

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

Например, один такой шаблон (код внутри макета):

= stylesheet_link_tag controller.controller_name

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

4b9b3361

Ответ 1

Наконец, выдумал это. Существование активов можно проверить следующим образом:
YourApp::Application.assets.find_asset("#{asset}.css").nil?

Тогда ответ будет следующим:

= stylesheet_link_tag controller.controller_name if YourApp::Application.assets.find_asset("#{controller.controller_name}.css")

Ответ 2

Я нашел этот ответ раньше, и мы с радостью использовали find_asset в нашем приложении (Rails 3.2.16), пока в один прекрасный день он не начал бомбить.

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

Короче говоря, find_asset не является пуленепробиваемым способом определить, доступен ли актив для включения. Вы можете прочитать кучу больше об этом в проблеме, которую кто-то пытался сообщить об этом, и который впоследствии был закрыт как не ошибка: https://github.com/sstephenson/sprockets/issues/411

Реальный способ определить, существует ли актив, и который работает как в режимах компиляции, так и в прекомпиляции, демонстрируется в обручах, чтобы файл вышеперечисленных проблем необходимо перескакивать. Здесь diff для его исправления: https://github.com/fphilipe/premailer-rails/pull/55/files

Я помещаю это здесь в надежде, что другие Гуглеры, которые найдут это, не попадут в ту же ловушку, что и я!

Ответ 3

Чтобы включить ресурс на основе имени контроллера

<% controller_asset = controller.controller_name %>
<%= stylesheet_link_tag controller_asset if YourApp::Application.assets.find_asset(controller_asset) %>

Чтобы включить актив на основе имени контроллера и имени действия (было полезно для меня)

<% action_asset = "#{controller.controller_name}/#{controller.action_name}" %>
<%= stylesheet_link_tag action_asset if YourApp::Application.assets.find_asset(action_asset) %>

И, конечно, лучше не оставлять этот код так, как есть, а скорее помещать его в помощника.

Ответ 4

= stylesheet_link_tag controller.controller_name if File.exists?(File.join(Rails.public_path, 'assets', "#{controller.controller_name}.css"))

Ответ 5

Простые ViewHelpers

Это то, что я использую сам. Добавьте это в свой ApplicationHelper:

module ApplicationHelper
  def controller_stylesheet(opts = { media: :all })
    if Rails.application.assets.find_asset("#{params[:controller]}.css")
      stylesheet_link_tag(params[:controller], opts)
    end
  end

  def controller_javascript(opts = {})
    if Rails.application.assets.find_asset("#{params[:controller]}.js")
      javascript_include_tag(params[:controller], opts)
    end
  end
end

и используйте их в своем application.html.haml:

= controller_stylesheet
= controller_javascript

Примечание.. Это работает со всеми .js,. coffee,.css,.scss, хотя он просто говорит .css и .js