Rails应用程序不能在生产环境中提供资源

在开发环境中运行我的应用程序工作正常。 在生产( rails server -e production ),浏览器不能访问CSS和JS文件,并在控制台上有这样的消息:

 I, [2013-07-27T21:00:59.105459 #11449] INFO -- : Started GET "/javascripts/application.js" for 99.102.22.124 at 2013-07-27 21:00:59 +0000 F, [2013-07-27T21:00:59.108302 #11449] FATAL -- : ActionController::RoutingError (No route matches [GET] "/javascripts/application.js"): 

在生产环境中来自html源头部分:

 <head> <title>a Social Server</title> <link data-turbolinks-track="true" href="/stylesheets/application.css" media="all" rel="stylesheet"> <link href="//netdna.bootstrapcdn.com/font-awesome/3.2.1/css/font-awesome.css" rel="stylesheet"> <script data-turbolinks-track="true" src="/javascripts/application.js"></script> <meta content="authenticity_token" name="csrf-param"> <meta content="jYM4IAXTXAuKWeD4FEVrXgXRNFeB6EazU68ZBQfRqNY=" name="csrf-token"> </head> 

另一方面在开发env头部分看起来像:

 <head> <title>a Social Server</title> <link data-turbolinks-track="true" href="/assets/application.css?body=1" media="all" rel="stylesheet"> <link data-turbolinks-track="true" href="/assets/twitter-bootstrap-static/bootstrap.css?body=1" media="all" rel="stylesheet"> <link data-turbolinks-track="true" href="/assets/twitter-bootstrap-static/fontawesome.css?body=1" media="all" rel="stylesheet"> <link data-turbolinks-track="true" href="/assets/bootstrap_and_overrides.css?body=1" media="all" rel="stylesheet"> <link data-turbolinks-track="true" href="/assets/instagram.css?body=1" media="all" rel="stylesheet"> <link data-turbolinks-track="true" href="/assets/socialserver.css?body=1" media="all" rel="stylesheet"> <link data-turbolinks-track="true" href="/assets/jquery.ui.core.css?body=1" media="all" rel="stylesheet"> <link data-turbolinks-track="true" href="/assets/jquery.ui.theme.css?body=1" media="all" rel="stylesheet"> <link data-turbolinks-track="true" href="/assets/jquery.ui.accordion.css?body=1" media="all" rel="stylesheet"> <link data-turbolinks-track="true" href="/assets/jquery.ui.menu.css?body=1" media="all" rel="stylesheet"> <link data-turbolinks-track="true" href="/assets/jquery.ui.autocomplete.css?body=1" media="all" rel="stylesheet"> <link data-turbolinks-track="true" href="/assets/jquery.ui.button.css?body=1" media="all" rel="stylesheet"> <link data-turbolinks-track="true" href="/assets/jquery.ui.datepicker.css?body=1" media="all" rel="stylesheet"> <link data-turbolinks-track="true" href="/assets/jquery.ui.resizable.css?body=1" media="all" rel="stylesheet"> <link data-turbolinks-track="true" href="/assets/jquery.ui.dialog.css?body=1" media="all" rel="stylesheet"> <link data-turbolinks-track="true" href="/assets/jquery.ui.progressbar.css?body=1" media="all" rel="stylesheet"> <link data-turbolinks-track="true" href="/assets/jquery.ui.selectable.css?body=1" media="all" rel="stylesheet"> <link data-turbolinks-track="true" href="/assets/jquery.ui.slider.css?body=1" media="all" rel="stylesheet"> <link data-turbolinks-track="true" href="/assets/jquery.ui.spinner.css?body=1" media="all" rel="stylesheet"> <link data-turbolinks-track="true" href="/assets/jquery.ui.tabs.css?body=1" media="all" rel="stylesheet"> <link data-turbolinks-track="true" href="/assets/jquery.ui.tooltip.css?body=1" media="all" rel="stylesheet"> <link data-turbolinks-track="true" href="/assets/jquery.ui.base.css?body=1" media="all" rel="stylesheet"> <link data-turbolinks-track="true" href="/assets/jquery.ui.all.css?body=1" media="all" rel="stylesheet"> <link href="//netdna.bootstrapcdn.com/font-awesome/3.2.1/css/font-awesome.css" rel="stylesheet"> <script data-turbolinks-track="true" src="/assets/jquery.js?body=1"></script> <script data-turbolinks-track="true" src="/assets/jquery_ujs.js?body=1"></script> <script data-turbolinks-track="true" src="/assets/twitter/bootstrap/bootstrap-transition.js?body=1"></script> <script data-turbolinks-track="true" src="/assets/twitter/bootstrap/bootstrap-alert.js?body=1"></script> <script data-turbolinks-track="true" src="/assets/twitter/bootstrap/bootstrap-modal.js?body=1"></script> <script data-turbolinks-track="true" src="/assets/twitter/bootstrap/bootstrap-dropdown.js?body=1"></script> <script data-turbolinks-track="true" src="/assets/twitter/bootstrap/bootstrap-scrollspy.js?body=1"></script> <script data-turbolinks-track="true" src="/assets/twitter/bootstrap/bootstrap-tab.js?body=1"></script> <script data-turbolinks-track="true" src="/assets/twitter/bootstrap/bootstrap-tooltip.js?body=1"></script> <script data-turbolinks-track="true" src="/assets/twitter/bootstrap/bootstrap-popover.js?body=1"></script> <script data-turbolinks-track="true" src="/assets/twitter/bootstrap/bootstrap-button.js?body=1"></script> <script data-turbolinks-track="true" src="/assets/twitter/bootstrap/bootstrap-collapse.js?body=1"></script> <script data-turbolinks-track="true" src="/assets/twitter/bootstrap/bootstrap-carousel.js?body=1"></script> <script data-turbolinks-track="true" src="/assets/twitter/bootstrap/bootstrap-typeahead.js?body=1"></script> <script data-turbolinks-track="true" src="/assets/twitter/bootstrap/bootstrap-affix.js?body=1"></script> <script data-turbolinks-track="true" src="/assets/twitter/bootstrap.js?body=1"></script> <script data-turbolinks-track="true" src="/assets/turbolinks.js?body=1"></script> <script data-turbolinks-track="true" src="/assets/bootstrap.js?body=1"></script> <script data-turbolinks-track="true" src="/assets/jquery.ui.core.js?body=1"></script> <script data-turbolinks-track="true" src="/assets/jquery.ui.widget.js?body=1"></script> <script data-turbolinks-track="true" src="/assets/jquery.ui.accordion.js?body=1"></script> <script data-turbolinks-track="true" src="/assets/jquery.ui.position.js?body=1"></script> <script data-turbolinks-track="true" src="/assets/jquery.ui.menu.js?body=1"></script> <script data-turbolinks-track="true" src="/assets/jquery.ui.autocomplete.js?body=1"></script> <script data-turbolinks-track="true" src="/assets/jquery.ui.button.js?body=1"></script> <script data-turbolinks-track="true" src="/assets/jquery.ui.datepicker.js?body=1"></script> <script data-turbolinks-track="true" src="/assets/jquery.ui.mouse.js?body=1"></script> <script data-turbolinks-track="true" src="/assets/jquery.ui.draggable.js?body=1"></script> <script data-turbolinks-track="true" src="/assets/jquery.ui.resizable.js?body=1"></script> <script data-turbolinks-track="true" src="/assets/jquery.ui.dialog.js?body=1"></script> <script data-turbolinks-track="true" src="/assets/jquery.ui.droppable.js?body=1"></script> <script data-turbolinks-track="true" src="/assets/jquery.ui.effect.js?body=1"></script> <script data-turbolinks-track="true" src="/assets/jquery.ui.effect-blind.js?body=1"></script> <script data-turbolinks-track="true" src="/assets/jquery.ui.effect-bounce.js?body=1"></script> <script data-turbolinks-track="true" src="/assets/jquery.ui.effect-clip.js?body=1"></script> <script data-turbolinks-track="true" src="/assets/jquery.ui.effect-drop.js?body=1"></script> <script data-turbolinks-track="true" src="/assets/jquery.ui.effect-explode.js?body=1"></script> <script data-turbolinks-track="true" src="/assets/jquery.ui.effect-fade.js?body=1"></script> <script data-turbolinks-track="true" src="/assets/jquery.ui.effect-fold.js?body=1"></script> <script data-turbolinks-track="true" src="/assets/jquery.ui.effect-highlight.js?body=1"></script> <script data-turbolinks-track="true" src="/assets/jquery.ui.effect-pulsate.js?body=1"></script> <script data-turbolinks-track="true" src="/assets/jquery.ui.effect-scale.js?body=1"></script> <script data-turbolinks-track="true" src="/assets/jquery.ui.effect-shake.js?body=1"></script> <script data-turbolinks-track="true" src="/assets/jquery.ui.effect-slide.js?body=1"></script> <script data-turbolinks-track="true" src="/assets/jquery.ui.effect-transfer.js?body=1"></script> <script data-turbolinks-track="true" src="/assets/jquery.ui.progressbar.js?body=1"></script> <script data-turbolinks-track="true" src="/assets/jquery.ui.selectable.js?body=1"></script> <script data-turbolinks-track="true" src="/assets/jquery.ui.slider.js?body=1"></script> <script data-turbolinks-track="true" src="/assets/jquery.ui.sortable.js?body=1"></script> <script data-turbolinks-track="true" src="/assets/jquery.ui.spinner.js?body=1"></script> <script data-turbolinks-track="true" src="/assets/jquery.ui.tabs.js?body=1"></script> <script data-turbolinks-track="true" src="/assets/jquery.ui.tooltip.js?body=1"></script> <script data-turbolinks-track="true" src="/assets/jquery.ui.all.js?body=1"></script> <script data-turbolinks-track="true" src="/assets/application.js?body=1"></script> <meta content="authenticity_token" name="csrf-param"> <meta content="jYM4IAXTXAuKWeD4FEVrXgXRNFeB6EazU68ZBQfRqNY=" name="csrf-token"> </head> 

该应用程序不使用数据库,所以我已禁用ActiveRecord。 configuration文件的片段:

application.rb中

 require File.expand_path('../boot', __FILE__) #require 'rails/all' require "action_controller/railtie" require "action_mailer/railtie" require "rails/test_unit/railtie" require "sprockets/railtie" Bundler.require(:default, Rails.env) module Socialserver class Application < Rails::Application end end 

production.rb

 Socialserver::Application.configure do config.cache_classes = true config.eager_load = true config.consider_all_requests_local = false config.action_controller.perform_caching = true config.serve_static_assets = false config.assets.js_compressor = :uglifier config.assets.compile = false config.assets.digest = true config.assets.version = '1.0' config.log_level = :info config.i18n.fallbacks = true config.active_support.deprecation = :notify config.log_formatter = ::Logger::Formatter.new config.assets.paths << Rails.root.join('app', 'assets', 'fonts') config.assets.precompile += %w( .svg .eot .woff .ttf ) end 

development.rb:

 Socialserver::Application.configure do config.cache_classes = false config.eager_load = false config.consider_all_requests_local = true config.action_controller.perform_caching = false config.action_mailer.raise_delivery_errors = false config.active_support.deprecation = :log config.assets.debug = true end 

的Gemfile:

 source 'https://rubygems.org' gem 'rails', '4.0.0' gem 'sass-rails', '~> 4.0.0' gem 'uglifier', '>= 1.3.0' gem 'coffee-rails', '~> 4.0.0' gem 'jquery-rails' gem 'jquery-ui-rails' gem 'turbolinks' gem 'jbuilder', '~> 1.2' group :doc do gem 'sdoc', require: false end group :twitter do gem 'twitter', '4.8.1' end group :instagram do gem 'instagram', '0.10.0' end group :tumblr do gem 'tumblr_client' end gem 'twitter-bootstrap-rails' gem 'therubyracer' #needed for runtime js on amazon ec2. 

我很抱歉张贴这么多的信息。 我觉得信息可能是相关的。

ps我只有一半的铁轨知识,所以请忍受我。 谢谢〜

在本地testing生产环境时,必须在本地编译资产。 只需运行下面的命令:

 RAILS_ENV=production bundle exec rake assets:precompile 

它将产生public/assets下的所有public/assets

接下来,你必须告诉Rails自己提供资产。 服务器软件(例如Nginx或者Apache)在Heroku这样的环境下为你做,但是在本地你应该让Rails去做。 在你的production.rb改变这个:

 config.serve_static_assets = true 

但是确保在将代码投入生产之前将其设置为false

这听起来像是我遇到的问题 。

我发现一个博客 ,这表明这是Rails 4.0.0资产pipe道中的一个错误,并通过设置莫名其妙地缓解…

 config.assets.compile = true 

…在config/environments/production.rb

除了以某种方式将资产pipe道踢到实际工作中,该设置将开启资产的实时编译。 对于生产性能来说,这通常是一件坏事,但如果在部署时仍然手动预编译资产,

 rake assets:precompile 

…实时编译不应该发生(因为必要的资源已经被预编译)。

我希望这有帮助 :)

如前所述,不build议使用config.serve_static_assets并将其replace为config.serve_static_files 。 如果你检查一下Rails-4.2的config/environments/production.rb ,那么你会发现:

  # Disable serving static files from the `/public` folder by default since # Apache or NGINX already handles this. config.serve_static_files = ENV['RAILS_SERVE_STATIC_FILES'].present? 

这意味着在运行rails s -e production之前,在会话中设置和导出(在BASH中)环境variablesexport RAILS_SERVE_STATIC_FILES="to any value whatsoever"会在本地testing时给出期望的结果,并且也将避免必须记住在推送到生产主机之前重新编码production.rb

在production.rb中改变设置:

导轨3.x

 config.serve_static_assets = true 

导轨4.x

 config.serve_static_files = true 

检查一个这样的文件:

 public/assets/.sprockets-manifest-3f7771d777ceb581d754e4fad88aa69c.json 

如果您将预编译的资源推送到生产服务器,则有可能阻止隐藏的“点”文件被推送,而这个重要的文件将无法投入生产。

在我的环境中,我需要在集成环境中预编译资产,并将其推送到生产环境,以便不需要在生产计算机上编译资产。 我错误地阻止了所有隐藏文件被推送到生产机器。

要查看此答案是否适合您,请在生产服务器的浏览器中检查生成的HTML源代码,以查看资产path是否已生成。 如果你看到你的脚本标签是这样的:

 <script data-turbolinks-track="true" src="/javascripts/application.js"></script> 

检查src属性。 它应该以/assets/javascript开头。 在这种情况下,它以/javascript开头,这表明Rails不认为任何资产已经预编译。

我通过更新我的推送到生产(当前rsync),以确保我在我的集​​成服务器上预编译后推送.sprockets-manifest*文件。

另外,我使用独立的Passenger作为我的集成testing服务器,而不是Webrick,因为它处理更真实的静态文件服务。

我认为到Rails 4.x你必须预编译资产生产或使用config.assets.compile甚至两者,如果需要的话。

生产环境的默认Rails行为是“如果预编译的资产被遗漏,不要回退到资产pipe道”。 所以,不要。 用于不compi

 config.assets.compile = false 

如果你使用这个选项,你不需要使用:

 config.serve_static_files = true 

因为如果资产没有预编译,Rails将在服务请求之前编译。

但是,如果您在生产之前预编译资源,则不需要config.assets.compile = true ,但是如果您没有http_server来提供预编译资产,则需要config.serve_static_files = true来处理Rails服务请求。

设置config.serve_static_assets已被弃用。

 DEPRECATION WARNING: The configuration option `config.serve_static_assets` has been renamed to `config.serve_static_files` to clarify its role (it merely enables serving everything in the `public` folder and is unrelated to the asset pipeline). The `serve_static_assets` alias will be removed in Rails 5.0. Please migrate your configuration files accordingly. 

我希望这个答案能帮助你(读者)理解真正发生的事情

以下命令适用于本地。

 rails server -e production 

在运行“rails s”的时候,我得到了同样的错误“ActionController :: RoutingError(没有路由匹配[GET]”/assets/application.css“”),甚至在我预编译源代码之后,改变了config precompile true,仍然无法加载正常。

选项“-e production”使那些RoutingError消失。