生产环境中的rack-zippy和选项-d不提供静态资产
我这里有一个非常奇怪的问题。 我在我的rails应用程序中使用rack-zippy
gem,如果我在没有预编译资产的development
环境中启动它,它就像一个魅力。 使用-d
param而不使用。
在生产模式(相同的机器,相同的项目,相同的目录,相同的gem),它也有效。 但是,如果我使用-d
param( bundle exec rails server -d
)启动它来守护服务器,则不会提供预编译的资产。 可以用thin
和webrick
重现,但不与unicorn
。
日志说:
ActionController::RoutingError (No route matches [GET] "/assets/application-b9b75968aed42128cfd75fb78df1e4d1.js"):
但:
$ l public/assets/application-b9b75968aed42128cfd75fb78df1e4d1.js -rw-r--r-- 1 public/assets/application-b9b75968aed42128cfd75fb78df1e4d1.js
来自config / environments / production.rb:
config.serve_static_assets = true
来自config / application.rb:
config.middleware.swap(ActionDispatch::Static, Rack::Zippy::AssetServer)
和:
$ rake middleware use Rack::Sendfile use Rack::Zippy::AssetServer (...)
我现在有些困惑。 有任何想法吗?
哎呀,我从来没有遇到过这个,但我会告诉你我的直觉,也许你可以在这里得到一些。 (感谢您在Github问题跟踪器上报告)。
所以独角兽是好的,但是薄而且我们不是,mmmm。
我的猜测是守护进程为thin和webrick使用的工作目录不是Rails.root。 您可能想尝试在rack-zippy中调试此行,以查看正在搜索资产文件的路径: https : //github.com/eliotsykes/rack-zippy/blob/master/lib/rack-zippy.rb #L87
rack-zippy从版本1.1.0开始(如果你使用的是最新的Gem,你可能正在使用它)传递所有请求,它无法找到一个文件,可用于剩余的中间件堆栈。
在开发+守护进程模式下,rack-zippy会将请求传递到资产管道,所以我认为我们可以假设资产管道在守护进程模式下没有问题。
在生产+守护进程模式下,资产管道可能已禁用(如您所愿),如果找不到资产文件,rack-zippy将向前传递请求(如果工作目录是不是Rails.root),然后剩下的中间件会给你看到的路由错误。
如果您在生产中启用了资产管道(非常不推荐),那么我预计路由错误会消失,而rack-zippy将不会做任何有用的事情。
对不起,我没有更坚实的东西继续下去。
在下一版本的rack-zippy中发布修复程序之前,要解决此问题,您可以使用此行(可能在config/application.rb
或config/initializers/rack_zippy.rb
):
Rails.application.config.middleware.swap(ActionDispatch::Static, Rack::Zippy::AssetServer)
替换为:
# Rails.public_path as last argument here gets passed into the Rack::Zippy::AssetServer # constructor to override the default asset_root argument value. Rails.application.config.middleware.swap(ActionDispatch::Static, Rack::Zippy::AssetServer, Rails.public_path)