Подтвердить что ты не робот

Добавление связанного с страницей CSS для Rails Asset Pipeline

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


У меня есть приложение Rails 3.1+, использующее конвейер активов. Там есть одно конкретное действие, которое я хочу использовать для разных CSS. (В моем конкретном случае у меня есть страница, предназначенная для печати, поэтому ей действительно нужен совершенно другой CSS и не нужен какой-либо Javascript.) В настоящее время у меня есть только один файл CSS для приложения. Как добавить новый CSS файл и настроить конвейер для использования моего файла?

Например, прямо сейчас мой app/assets выглядит как

app/assets
    /javascript
        application.js
        custom.js.coffee
    /css
        application.css
        custom.css.scss

Я хочу добавить файл print.css, который используется в представлении определенного действия. Это представление не будет использовать файл application.css. Как добавить print.css?

4b9b3361

Ответ 1

Я нашел этот пост в блоге очень полезным: http://blog.seancarpenter.net/2012/11/05/page-specific-javascript-with-the-asset-pipeline/. Мой ответ перефразирует то, что написал этот блоггер, и заполняет несколько недостающих деталей.


Во-первых, важно, чтобы вы прочитали и поняли Руководство по Rails для конвейера активов. К сожалению, в этом руководстве нет четкого объяснения того, как добавлять активы, зависящие от конкретных действий, но он охватывает некоторые концепции, которые вам нужно знать. Удостоверились, что вы понимаете эти идеи:

  • Что конвейер активов компилирует Javascript, CSS и другие активы, чтобы серверы Rails могли кэшировать активы для лучшей производительности.
  • В файлах манифеста используются команды типа require, require_tree и require_self, чтобы указать, какие файлы скомпилированы вместе.
  • Чтобы для надлежащего функционирования конвейера активов в процессе производства вам нужно вручную запустить rake assets:precompile для создания скомпилированных, обобщенных активов в каталоге public.

Эти идеи являются минимальными "необходимыми для изучения" сведениями о конвейере активов. Если вы еще не понимаете эти идеи, у вас нет уровня знаний "экспертов" или "энтузиастов" о конвейере, и, к сожалению, SO не подходит для изучения этого материала. К счастью, Rails Guide для Asset Pipeline - это короткое 15-минутное чтение, и вы можете быстро ускорить его, если вам это нужно.


Во-вторых, это изменения, которые необходимо внести, чтобы убедиться, что конвейер ресурсов правильно видит и обрабатывает ваш новый файл print.css.

Выполните следующие действия:

  • Добавьте ваш print.css файл в app/assets/css.
  • Вам нужно создать файл манифеста, в котором будет отображаться Rails, где можно найти print.css. Вам нужно сделать это, даже если у вас есть только один файл CSS, который вы добавляете. Это простой шаг:
    • Добавьте файл print.js в app/assets/javascript.
    • Добавьте эту строку в print.js:
//= require print

Это будет единственная строка во всем файле print.js. Если я правильно понимаю, Rails ожидает, что файлы манифеста будут иметь расширение файла .js, поэтому мы не используем print.css в качестве файла манифеста.

  1. Теперь нам нужно указать Rails, чтобы найти и использовать манифест print.js. Добавьте в свой файл config/application.rb следующую строку:
config.assets.precompile += %w( print.js )
  1. Мы почти закончили! Однако уже существующий манифест application.js включает в себя строку //= require_tree ., что означает, что он будет содержать ваш файл print.css. Это приведет к тому, что ваш стиль print.css повлияет на весь ваш сайт, а не только на один вид. Есть два способа справиться с этим:
    • Если application.js и print.js не имеют общих ресурсов, вы можете использовать команду stub в application.js, чтобы исключить активы, используемые в print.js. Это дает указание application.js удалить любое из активов, которое print.js ссылается на собственный список ссылочных файлов. Наш измененный application.js выглядит так:
(snip...)
require_tree .
stub print

Подробнее см. этот ответ.

  • Если ваши файлы print.js и application.js разделяют некоторые активы, вам необходимо переместить все активы, используемые application.js в подкаталоги. Я не делал этого сам, поэтому я не очень помог в этой области. Посмотрите этот ответ для получения инструкций.

Теперь мы включили print.css в конвейер активов. Теперь нам нужно направить Rails на использование print.css в вашем конкретном представлении.

Скажем, ваше действие находится в контроллере reports и что действие называется print_reports. Это означает, что у нас есть файл reports_controller.rb и файл print_reports.html.erb (или .haml). Мы должны внести несколько изменений в эти файлы.

  • Чтобы начать, добавьте новый макет в app/views/layouts. Возможно, назовите его print.html.erb. Мы будем использовать этот новый макет для вашего файла print_reports.html.erb. Настройте его по своему усмотрению. Для страницы, предназначенной для печати, это, вероятно, будет очень просто, например
<html>
    <head>
        <title="Print">
    </head>
    <body>
        <%= yield %>
    </body>
</html>

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

  1. Добавьте stylesheet_link_tag в заголовок макета, указав на ваш print.css:
<html>
    <head>
        <title="Print"/>
        <%= stylesheet_link_tag "print" %>
    </head>
    <body>
        <%= yield %>
    </body>
</html>
  1. В контроллере мы скажем Rails использовать наш новый макет для действия. Добавьте строку layout 'print', only: [:print_reports] к контроллеру:
class reports_controller < ApplicationController
    layout 'print', only: [:print_reports]

    #snip

См. этот вопрос для получения дополнительной информации и нескольких разных подходов.

В этот момент, когда вы запускаете приложение, ваше действие print_reports должно корректно использовать print.css!


Не забудьте запустить rake assets:precompile перед развертыванием на сервере.

Ответ 2

В вашем макете

<head>
  // ...
  <%= yield :stylesheets %>
</head>

На ваш взгляд

<%= provide :stylesheets do %>
  // your page-specific css
<% end %>