我需要在我的 engine.rb 中明确包含依赖项,以便其资产最终出现在我的资产管道中。不知道为什么这是必要的,因为阿拉斯托的回答对我来说听起来是正确的。值得注意的是,依赖项是我使用捆绑器创建的 gem,尽管我不明白为什么这会产生影响。
module MyRailsPluginFull
class Engine < ::Rails::Engine
require 'dependency1'
require 'dependency2'
end
end
添加于 2012 年 11 月 23 日
在花了更多时间与引擎合作之后,我想我现在更充分地理解了这一点。 Gemspec 只是所需依赖项的列表,但 Gemspec 不会指示应用程序在启动时从这些依赖项加载文件。另一方面,Gemfiles 会在启动期间加载所有文件。
添加于 2015 年 3 月 20 日
我两年多前的说法“另一方面,Gemfiles 会在启动期间加载所有文件”并不完全正确。这在 Rails 中基本上是正确的,默认情况下运行Bundler.require
需要 Gemfile 中列出的所有依赖项,如生成器文件中所示here https://github.com/rails/rails/blob/v4.2.1/railties/lib/rails/generators/rails/app/templates/config/application.rb#L20-- 请注意,虽然 Rails 的默认行为如所讨论的从 Rails3 更改为 Rails 4here https://github.com/rails/rails/commit/49c4af43ec5819d8f5c1a91f9b84296c927ce6e7,两者都使用Bundler.require
。然而,有充分的理由使用Bundler.setup
然后一个明确的require "dependency1"
在实际依赖的文件中depedency1
.
See 这次讨论 http://anti-pattern.com/use-bundler-setup-instead-of-bundler-require of Bundler.require
versus Bundler.setup
.
此外,正如 @nruth 在评论中指出的那样,这可能会导致加载不必要的类。然而,如果依赖关系设计良好,它的类大部分都会自动加载,从而为需要整个依赖关系创造最小的开销。或者,如果它在一个可以单独需要的文件中定义其引擎,您可以只包含该引擎文件,该文件应该将必要的文件添加到您的资源路径中,从而允许您在 CSS 和 JS 清单中需要其资源。看这个 bootstrap-sass 示例 https://github.com/twbs/bootstrap-sass/blob/v3.3.4/lib/bootstrap-sass/engine.rb,其中 gem 都将其所有资产添加到config.assets.paths
并将其中一些添加到config.assets.precompile
.
虽然这个问题已经有几年了,我什至不记得当时我在写什么 Rails Engine,但我怀疑正确的方法应该更接近这个:
module MyRailsPluginFull
class Engine < ::Rails::Engine
initializer 'bootstrap-sass.assets.precompile' do |app|
require 'dependency1'
# add dependency1's assets to the list of paths
app.config.assets.paths << ...
end
end
end
但请注意,这不是必需的 - 依赖项本身应该定义此初始值设定项,以便仅需要它就足够了,就像上面的引导示例一样。