Rails 4:未在生产中加载的资产

eme*_*his 116 ruby ruby-on-rails asset-pipeline ruby-on-rails-4

我正在尝试将我的应用程序投入生产,图像和css资产路径无法正常工作.

这是我目前正在做的事情:

  • 图片资产位于/app/assets/images/image.jpg中
  • 样式表位于/app/assets/stylesheets/style.css中
  • 在我的布局中,我像这样引用css文件: <%= stylesheet_link_tag "styles", media: "all", "data-turbolinks-track" => true %>
  • 在重新启动独角兽之前,我运行RAILS_ENV=production bundle exec rake assets:precompile并且它成功了,我在public/assets目录中看到了指纹文件.

当我浏览到我的网站时,我收到404找不到错误mysite.com/stylesheets/styles.css.

我究竟做错了什么?

更新: 在我的布局中,它看起来像这样:

<%= stylesheet_link_tag    "bootstrap.min", media: "all", "data-turbolinks-track" => true %>
<%= stylesheet_link_tag    "styles", media: "all", "data-turbolinks-track" => true %>
<%= javascript_include_tag "application", "data-turbolinks-track" => true %>
Run Code Online (Sandbox Code Playgroud)

生成源是这样的:

<link data-turbolinks-track="true" href="/stylesheets/bootstrap.min.css" media="all" rel="stylesheet" />
<link data-turbolinks-track="true" href="/stylesheets/styles.css" media="all" rel="stylesheet" />
<script data-turbolinks-track="true" src="/assets/application-0c647c942c6eff10ad92f1f2b0c64efe.js"></script>
Run Code Online (Sandbox Code Playgroud)

看起来Rails没有正确地查找已编译的css文件.但是为什么它适用于javascripts(注意/assets/****.js路径)是非常令人困惑的.

Ram*_*are 103

在rails 4中,您需要进行以下更改:

config.assets.compile = true
config.assets.precompile =  ['*.js', '*.css', '*.css.erb'] 
Run Code Online (Sandbox Code Playgroud)

这适用于我.使用以下命令预编译资产

RAILS_ENV=production bundle exec rake assets:precompile
Run Code Online (Sandbox Code Playgroud)

祝你好运!

  • 我认为将config.assets.compile设置为true会导致生产中的性能下降.还有,css.erb?谁用那个?那咖啡和咖啡怎么样? (11认同)
  • 对不起,我无法连接你所说的回答我的问题. (4认同)
  • 通常,当您运行生产服务器时,您将在 Apache 或 nginx Web 服务器后面使用乘客或独角兽或 puma 来运行 Rails。最好让 Apache 或 nginx 服务静态文件(js、css、图像),而 Rails 应用服务器(puma、unicorn)服务 Rails 代码和模板。为此,您应该关闭“config.serve_static_files”,并在 Apache 和 nginx 中配置别名来处理“assets”。 (2认同)

dav*_*mac 84

我刚遇到同样的问题,在config/environments/production.rb中找到了这个设置:

# Rails 4:
config.serve_static_assets = false

# Or for Rails 5:
config.public_file_server.enabled = false
Run Code Online (Sandbox Code Playgroud)

改变它以true使其工作.看来默认情况下,Rails希望您已经配置了前端Web服务器来处理公共文件夹外的文件请求,而不是将它们代理到Rails应用程序.也许你已经为你的javascript文件而不是你的CSS样式表做了这个?

(参见Rails 5文档).如评论中所述,使用Rails 5,您可以设置RAILS_SERVE_STATIC_FILES环境变量,因为默认设置是config.public_file_server.enabled = ENV['RAILS_SERVE_STATIC_FILES'].present?.

  • Rails 5.0.0.1 config/environments/production.rb包含`config.public_file_server.enabled = ENV ['RAILS_SERVE_STATIC_FILES'].present?`因此您可以针对您的环境设置不同的内容,而无需更改已签入SCM的代码. (3认同)
  • 这应该是公认的答案.虽然它是Rails*4.2*中的`config.serve_static_files`和Rails*5*中的`config.public_file_server.enabled`.@see https://github.com/heroku/rails_serve_static_assets/blob/master/lib/rails_serve_static_assets/railtie.rb (2认同)

eme*_*his 32

/config/environments/production.rb我必须添加这个:

Rails.application.config.assets.precompile += %w( *.js ^[^_]*.css *.css.erb )
Run Code Online (Sandbox Code Playgroud)

.js已经预编译了,但无论如何我添加了它..css和.css.erb显然不会自动发生.在^[^_]不包括来自谐音被编译-这是一个正则表达式.

有些令人沮丧的是,文档清楚地说明默认情况下启用了资产管道IS,但没有说明只适用于javascripts的事实.


Yan*_*sky 23

我能够通过改变来解决这个问题: config.assets.compile = false
config.assets.compile = true/config/environments/production.rb

更新(2018年6月24日):如果您使用的Sprockets版本低于2.12.5,3.7.2或4.0.0.beta8,则此方法会创建一个安全漏洞

  • 这是不是意味着Rails正在编译资产而不是从CDN加载它们? (7认同)
  • 此模式使用更多内存,性能比默认值更差,不建议使用.最好使用nginx代理. (2认同)

ytb*_*yan 13

对于Rails 5,您应该启用以下配置代码:

config.public_file_server.enabled = true

默认情况下,Rails 5附带此配置行:

config.public_file_server.enabled = ENV['RAILS_SERVE_STATIC_FILES'].present?

因此,您需要将环境变量设置RAILS_SERVE_STATIC_FILES为true.


Châ*_*ĩnh 10

在生产中为资产提供服务必须完成两件事:

  1. 预编译资产.
  2. 将服务器上的资产提供给浏览器.

1)为了预编译资产,您有多种选择.

  • 您可以rake assets:precompile在本地计算机上运行,将其提交到源代码控制(git),然后运行部署程序,例如capistrano.这不是将预编译资产提交给SCM的好方法.

  • RAILS_ENV=production rake assets:precompile在重新启动服务器之前,每次将Rails应用程序部署到生产环境时,都可以编写在目标服务器上运行的rake任务.

capistrano任务中的代码看起来类似于:

on roles(:app) do
  if DEPLOY_ENV == 'production'
    execute("cd #{DEPLOY_TO_DIR}/current && RAILS_ENV=production rvm #{ruby_string} do rake assets:precompile")
  end
end
Run Code Online (Sandbox Code Playgroud)

2)现在,您拥有生产服务器上的资产,您需要将它们提供给浏览器.

同样,你有几个选择.

  • config/environments/production.rb中打开Rails静态文件服务

    config.serve_static_assets = true # old
    
    or
    
    config.serve_static_files = true # new
    
    Run Code Online (Sandbox Code Playgroud)

    使用Rails提供静态文件将会破坏您的Rails应用程序性能.

  • 配置nginx(或Apache)以提供静态文件.

    例如,配置为与Puma一起使用的我的nginx如下所示:

    location ~ ^/(assets|images|fonts)/(.*)$ {
        alias /var/www/foster_care/current/public/$1/$2;
        gzip on;
        expires max;
        add_header Cache-Control public;
    }
    
    Run Code Online (Sandbox Code Playgroud)