CarrierWaveで複数画像扱うときは配列形式で保持する必要がある
seedファイルでuserとpostのダミーデータを以下の内容で作成しbundle exec rails db:seed
で実行したところ、postsの生成のところでArgumentError: invalid byte sequence in UTF-8
が出て生成が失敗してしまいました。
#usersのseedファイル puts 'Start inserting seed "users" ...' 10.times do user = User.create!( email: Faker::Internet.unique.email, username: Faker::Internet.unique.user_name, password: 'password', password_confirmation: 'password' ) puts "\"#{user.username}\" has created!" end
#postsのseedファイル puts 'Start inserting seed "posts" ...' User.limit(10).each do |user| post = user.posts.create!( body: Faker::Hacker.say_something_smart, images: File.open("#{Rails.root}/db/fixtures/dummy.png") ) puts "post#{post.id} has created!" end
原因
調べたところこちらのサイト( carrierwaveを使った画像のseed方法 )のものと同様で、CarrierWaveで複数画像扱うように設定していたので画像は配列形式で格納しなければならなかったということでした。
対応内容
postsのseedファイルの
images: File.open(“#{Rails.root}/db/fixtures/dummy.png")
の部分を下記のように配列形式に変更しました。
images: [File.open("#{Rails.root}/db/fixtures/dummy.png")]
これで無事ダミーデータが生成されました!
CarrierWaveで複数画像を扱う場合
・画像情報を格納するカラム名を複数形にする。(image => images)
・データベースがjsonのデータ型をサポートしている場合(PostgreSQL, MySQLなど)はデータ型をJSONにする。
#例 def change create_table :posts do |t| t.json :images, null: false t.text :body, null: false t.references :user, foreign_key: true t.timestamps end
データベースがjsonのデータ型をサポートしていない場合(SQLiteなど)はstring型にし、モデル側でserialize :images, JSON
と記載する。
#例 class Post < ApplicationRecord belongs_to :user mount_uploaders :images, PostImageUploader serialize :images, JSON validates :images, presence: true validates :body, presence: true, length: {maximum: 1000} end
・モデルとアップローダーとの紐付けの設定の際、モデルにmount_uploaders(複数形) :images(カラム名複数形), PostImageUploader(アップローダー名)
のように複数形にして記載する。
・コントローラ上のストロングパラメータも画像の部分は空の配列を記載する
params.require(:post).permit(:body, images: [])
・ビュー上の画像を選択するフィールドにはmultiple: true
で複数選択できるようにする。
(例) = f.file_field :images, multiple: true, class: 'form-control'