はじめに
Rails勉強中のエンジニア初心者が他の記事を参考にしたり、実際に実装してみたりして、アウトプットの一環としてまとめたものです。
間違っていることもあると思われるので、その際は指摘いただけると幸いです。
Railsガイド
Railsでの画像アップロード
代表的な方法として下記2つのパターンがあるが、1について記載する。
Rails5.1まではcarrierwave
というGem
のインストールが一般的であったが、
Rails5.2以降はActive storage
という便利機能が追加されたため、新たなGem
のインストールは不要となった。
-
Active Storage
とimage_processing
を使用する -
carrierwave
とmini_magic
を使用する
Active Storageとは
-
Active Storage
は、Rails5.2で追加されたファイルアップロードを行うための機能で、フォームでの画像の投稿機能などが簡単に実装できる -
Amazon S3
、Google Cloud Storage
、Microsoft Azure Storage
などのクラウドストレージサービスに対しても、ファイルのアップロードを簡単に行うことができる - クラウドストレージの他に、ローカルディスクにファイルを保存することもでき、開発環境ではローカルストレージにファイルを保存して、本番環境ではクラウドストレージにファイルを保存するなど、環境毎に保存先を切り替えることもできる
-
Paperclip
、Carrierwave
、Dragonfly
などのGem
の代わりになると言われている
Active Storageをインストールする
rails active_storage:install
を実行するとActive Storageを使用するために必要となるテーブルを作成するためのマイグレーションファイルが自動で作成される(active_storage_bolds
、active_storage_attachements
、active_storage_variant_records
)
実行コマンド
rails active_storage:install
rails db:migrate
Active Storageの実装
モデルの編集
Active Storage
を使って画像などのデータを既存のテーブルと紐づけるために、
モデルファイルにhas_one_attached :カラム名
を追加する(has_one_attached
はActive Storage
で使う指定方法)。
シンボルで指定するカラム名でそのデータを扱うため分かりやすい名称にする。例えば、画像なら
:image
、動画なら:movie
、アバターなら:avatar
など。
モデルファイルへの記載方法
```ruby
# 1ファイルの場合
has_one_attached :image
# 複数ファイルの場合
has_many_attached :images
```
実際の記述例
# Roomモデルにアイコンとして画像を1つ紐づける場合
class Room < ApplicationRecord
has_one_attached :image
end
コントローラの編集
モデルファイルで関連付けたActive Storageのデータをパラメータで受け取ることができるように、ストロングパラメータに対象のカラム名を追加する。
-
実際の記述例
class RoomsController < ApplicationController def create @room = Room.new(room_params.merge(user_id: current_user.id)) if @room.save flash[:notice] = "ルームを登録しました" redirect_to :rooms end end private def room_params params.require(:room).permit(:room_name, :room_introduction, :usage_fee, :address, :image) end end
ビューの編集
-
ビューへの記載方法
# 画像を登録するフォーム <%= form.file_field :image %> # 登録されている画像を表示する <%= image_tag @room.image %>
-
実際の記述例
# 登録フォーム <%= form_with model: room do |f| %> <%= f.label :image, 'ルーム画像' %> <%= f.file_field :image, required: true %> <%= f.submit '登録', class: 'submit-button' %> <% end %>
# 画像の表示 # 画像が登録されていないとエラーになるため、if room.image.attached?で画像が登録されている場合のみ表示する <% @rooms.each do |room| %> <%= link_to(new_reservation_path(id: room.id)) do%> <p><%= image_tag(room.image.variant(resize: 399)) if room.image.attached? %></p> <% end %> <% end %>
画像のサイズ変換
アップロードした画像をビューで表示するときに画像サイズを変換することができる。一覧ページでは画像サイズを100×100で表示し、詳細ページでは300×300で表示する場合などは、Active Storage
のvariant
(バリアンと)という機能を使用する。
variant
を使用すると、アップロードした画像を基にして簡単に画像のサイズを変更することが作成できる。
variant
を使用するためには、ImageProcessing
というGem
をインストールする必要がある。
# Use Active Storage variant
gem 'image_processing', '~> 1.2'
ImageProcessing
は内部の画像プロセッサとしてMiniMagick
というGem
を使用しており、MiniMagick
はImageMagick
というソフトウェアのGem
版であるため、ImageMagick
がインストールされていないと動かない。
ImageMagick
>>MiniMagick
>>ImageProcessing
>>variant
という流れ
そのため、ImageProcessingを使うためには、ImageMagickをインストールする必要がある。
この手順は本番環境でも行う必要があるため注意が必要。
# Macの場合
$ brew install imagemagick
# Ubuntuの場合
$ sudo apt-get install imagemagick
# バージョン確認
$ convert --version
-
variantによる画像のリサイズ
<%= image_tag room.image.variant(resize: 399) %>
-
オプション一覧
オプション 説明 gravity 画像変換の始点。convert -list gravityで指定値一覧を表示(デフォルトはNone)。 resize 画像のサイズ。詳しくは Image Geometry - ImageMagick 参照。 crop 始点からの切り抜きサイズ。 precessed 既に変換済みであれば変換しない(キャッシュを表示)。
参考