Rails 4 - Carrierwave图片无法上传

4
更新:感谢大家帮助解决问题。我决定放弃学习并在个人资料模型中添加另一个图像属性,目前只能这样做。

我正在尝试在Rails 4中制作一个应用程序。

我有一个用户模型,其中包含一个头像属性。

我还有一个个人资料模型。

User:拥有一个profile Profile:属于User

我将它们分开的原因是因为profile包含所有变量,而user包含所有不能在没有管理员权限的情况下更改的固定属性。

例外情况是我的用户模型有一个头像(image)属性,我想允许用户更改。

我在代码的其他部分使用了user carrierwave,它可以正常工作。但是,在这种情况下出现了问题。

我有一个avatar uploader:

class AvatarUploader < CarrierWave::Uploader::Base

  # Include RMagick or MiniMagick support:
  # include CarrierWave::RMagick
  include CarrierWave::MiniMagick

  # Choose what kind of storage to use for this uploader:
  # storage :file
  storage :fog

  # Override the directory where uploaded files will be stored.
  # This is a sensible default for uploaders that are meant to be mounted:
  def store_dir
    "uploads/#{model.class.to_s.underscore}/#{mounted_as}/#{model.id}"
  end

  def cache_dir
    "#{Rails.root}/tmp/uploads"
  end

  # Provide a default URL as a default if there hasn't been a file uploaded:
  # def default_url
  #   # For Rails 3.1+ asset pipeline compatibility:
  #   # ActionController::Base.helpers.asset_path("fallback/" + [version_name, "default.png"].compact.join('_'))
  #
  #   "/images/fallback/" + [version_name, "default.png"].compact.join('_')
  # end

  # Process files as they are uploaded:
  # process :scale => [200, 300]
  #
  # def scale(width, height)
  #   # do something
  # end

  # Create different versions of your uploaded files:
  # version :thumb do
  #   process :resize_to_fit => [50, 50]
  # end

  process :resize_to_fit => [800, 800]
  # Create different versions of your uploaded files:
  version :thumb do
    process :resize_to_fill => [200,200]
  end

  version :profile do
    process :resize_to_fill => [345,245]
  end

  version :wide do
    process :resize_to_fill => [951,245]
  end

  version :preview do
    process :resize_to_fill => [90,90]
  end

  version :small do
    process :resize_to_fill => [35,35]
  end


  # Add a white list of extensions which are allowed to be uploaded.
  # For images you might use something like this:
  def extension_white_list
     %w(jpg jpeg gif png)
  end

  # Override the filename of the uploaded files:
  # Avoid using model.id or version_name here, see uploader/store.rb for details.
  # def filename
  #   "something.jpg" if original_filename
  # end

end

在我的用户模型中,我有以下内容:
class User < ActiveRecord::Base
  mount_uploader :avatar, AvatarUploader
end

在我的用户控制器中,我在 strong params 中将 :avatar 列入白名单。

在我的个人资料控制器的 strong params 中,我尝试添加:

params.require(:profile).permit(:title, :overview, user_attributes: [:avatar])

我也尝试在我的个人资料模型中允许用户属性(如下所示):

belongs_to :user
accepts_nested_attributes_for :user

我在views用户文件夹中有一个部分表单。

<%= simple_fields_for :user,  html: { multipart: true } do |f| %>
  <%= f.error_notification %>
  <div class="form-inputs">
    <%= f.input :avatar, as: :file, :label => "Add a profile image (head shot)" %>
  </div>
<% end %>

那部分被包含在我的个人资料表单中。 然后,我想在我的个人资料展示视图中显示用户头像:
<div class="col-md-5 col-lg-4 vc-photo" style= "background-image: url(<%= image_url @profile.user.avatar.url if @profile.user.avatar? %>);">&nbsp;</div>

然而,它只是呈现了一个空白页面。

我尝试过:

但它仍然只是呈现为空白页。

有人能看出我做错了什么吗?

当我在Rails控制台中检查用户头像时,我得到了这个:

u.avatar => #, last_sign_in_ip: #, confirmation_token: "73abb47df224dbc3a612b46ced66e1aba...", confirmed_at: "2016-04-02 07:13:57", confirmation_sent_at: "2016-04-02 22:59:44", unconfirmed_email: "testiest@gmail.com", failed_attempts: 0, unlock_token: nil, locked_at: nil, created_at: "2016-04-02 07:13:57", updated_at: "2016-04-02 22:59:43", avatar: nil, approved: false>, @mounted_as=:avatar>

采纳以下建议

我改变了我的表单,所以现在个人资料表单有:

  <%= render 'users/profileimgform', f: f %>

现在用户/个人资料图片表单包括:

<%= simple_fields_for :user,  html: { multipart: true } do |ff| %>
  <%= f.error_notification %>

              <div class="form-inputs">


              <%= ff.input :avatar, as: :file, :label => "Add a profile image (head shot)" %>

              </div>


        <% end %>

我不确定是否需要在我的个人资料表单中加入“ff”。我尝试用“ff”替换最后一个“f”,但出现了一个错误,询问我它应该是一个单独的“f”。

当我尝试这样做时,控制台仍然显示用户的头像为“nil”。


所以图像不是空的,对吧?你可以在控制台尝试一下。 - MaicolBen
它是nil。我在上面添加了Rails c的输出。 - Mel
my_file_path.jpg 是指向 Rails 应用程序中文件的路径。 - MaicolBen
什么是“later”?我想现在就让它工作。 - Mel
在开发中修复它,一旦它在storage :file中工作正常,就可以轻松使用storage :fog - 7urkm3n
显示剩余10条评论
4个回答

1

我猜你在这段代码中出现了错误:

<%= simple_fields_for :user,  html: { multipart: true } do |f| %>
  <%= f.error_notification %>
  <div class="form-inputs">
    <%= f.input :avatar, as: :file, :label => "Add a profile image (head shot)" %>
  </div>
<% end %>

查看生成的HTML代码。我认为应该有类似以下内容:

<%= simple_form_for :profile do |f| %>
  ...
  <%= f.simple_fields_for :user do |ff| %>
    <%= ff.input :avatar %>
  <% end %>
<% end %>

嗨,Alex,我尝试了这个 - 我更新了我的问题以展示我的尝试。我的user.avatar仍然是nil。 - Mel
嗨,Alex - 你想看哪一部分?我想在个人资料展示页面上显示头像?我可以在控制台中看到头像为nil,所以它没有保存到数据库中。 - Mel
<%= simple_fields_for :user, html: { multipart: true } do |ff| %> <%= ff.error_notification %>
<%= ff.input :avatar, as: :file, :label => "添加个人头像" %>
<% end %>
- Mel
抱歉 Alex。我不知道那是什么意思。 - Mel

0
请注意,嵌套表单或复杂表单应使用form_forfields_for帮助程序连接模型和关联,例如:
<%= form_for @person do |f| %>
  Addresses:
  <ul>
    <%= f.fields_for :addresses do |addresses_form| %>
      <li>
        <%= addresses_form.label :kind %>
        <%= addresses_form.text_field :kind %>
      </li>
    <% end %>
  </ul>
<% end %>

连接模型和关联的方法是

  • form_for @person 构建 person 表单实例 f
  • 使用 person 表单实例 f 构建关联表单 f.fields_for :addresses 实例 addresses_form
  • 使用关联表单输入上传文件 addresses_form.input ...

最后,我猜想 simple_fields_for 是 simple_form 的 额外帮助程序,也许它只适用于 form_for 帮助程序。


这是一个关于给定模型和控制器的示例:

app/models/user.rb

class User < ActiveRecord::Base
  mount_uploader :avatar, AvatarUploader
  has_one :profile
end

app/models/profile.rb

class Profile < ActiveRecord::Base
  belongs_to :user
  accepts_nested_attributes_for :user
end

实际上,修改模型的嵌套属性有两种方法。

  1. 在同一个表单中同时修改模型和嵌套属性

您应该构建一个包含您的模型和关联的复杂表单

更多信息:http://guides.rubyonrails.org/form_helpers.html#building-complex-forms

app/controllers/profile_controller.rb

class ProfileController < ApplicationController

  private

  def profile_params
    params.require(:profile).permit(:title, user_attributes: [:avatar])
  end
end

app/views/profile/edit.html.erb

<%= form_for :profile do |f| %>
  Avatar:
  <ul>
    <%= f.fields_for :user do |uf| %>
      <li>
        <%= uf.label :avatar %>
        <%= uf.file_field :avatar %>
      </li>
    <% end %>
  </ul>
<% end %>
  1. 仅修改嵌套属性

您可以为该关联属性构建一个普通表单,但是当您必须初始化它时,这会变得棘手和模糊,因此我不愿在此提供示例代码,以免让您感到困惑。


@user2860931,当你处理嵌套表单时会变得复杂,这篇文章也许能帮到你:http://www.sitepoint.com/complex-rails-forms-with-nested-attributes/ - abookyun

0

我通过将头像从用户移到个人资料中来解决了这个问题。


0

我遇到了同样的错误。如果你使用的是Mac电脑,请尝试重新安装ImageMagick。我使用了Homebrew。你只需要运行这个命令:

brew install imagemagick

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接