Help us understand the problem. What is going on with this article?

Railsでアップローダを作って覚えるCarrierwaveのチュートリアル

More than 5 years have passed since last update.

概要

Carrierwaveのサンプルコードは、画像の処理とscaffoldが多いので自力でアップローダを作ってみるチュートリアルを作りました。
最低限Railsが動く状態からスタートすることを想定しています。

実装手順

ライブラリを準備する

Gemfileに以下の行を追加

gem 'carrierwave'

以下のコマンドでインストール

bundle install

モデルを準備する

carrierwaveのuploaderを生成する

rails generate uploader UploadFile

uploaderの細かい設定を行いたい場合には、 /app/uploaders/upload_file_uploader.rb を変更する。

コマンドでファイルを扱うためのモデルを作成

rails generate model UploadFile name:string file:string

以下のコマンドでDBを生成

rake db:migrate

生成したモデルに、mount_uploaderを追加する。
このときに追加するのは、rails generate uploaderで生成したUploadFileなので、
末尾にUploaderを追加して、UploadFileUploaderになる。

/app/models/upload_file.rb
class UploadFile < ActiveRecord::Base
+  mount_uploader :file, UploadFileUploader
end

これでモデルに関する部分は完成。

UIからアップロードできるようにする

アップロードするためのWebの処理を作成する

後から使うdownloadやindexも同時に生成しておく

rails generate controller uploader index form upload download

フォームを用意する

/app/views/uploader/form.html.erb
    <% @upload = UploadFile.new %>
    <%= form_for @upload, :url => {:action => :upload} do |f| %>
      <%= f.label :name, "name" %>
      <%= f.text_field :name %>
      <%= f.label :file %>
      <%= f.file_field :file %>
      <%= f.submit "Upload" %>
    <% end %>

コントローラの生成時に自動的に生成されたroutes.rbがPOSTを受け取るように手直しする。

/config/routes.rb
+  post 'uploader/upload'
-  get 'uploader/upload'

ファイルを保存してindexにリダイレクトする処理をコントローラに追加

/app/controllers/uploader_controller.rb
  def upload
    @upload_file = UploadFile.new( params.require(:upload_file).permit(:name, :file) )
    @upload_file.save
    redirect_to action: 'index'
  end

アップロードしたファイル一覧を見れるようにする

アップロードされたファイルの一覧を確認する。

/app/views/uploader/index.html.erb
    <%= link_to 'アップロードはこちら', action: "form" %>
    <ul>
      <% UploadFile.all.reverse_order.each do |upload| %>
        <li><%= link_to upload.name, action: "download", id: upload.id %>
      <% end %>
    </ul>

ダウンロードできるようにする

ダウンロードにはRailsのdownload用のメソッドsend_fileを使う
uploderのcurrent_pathを指定してダウンロードできるようにしている。

/app/controllers/uploader_controller.rb
  def download
+    @upload_file = UploadFile.find(params[:id].to_i)
+    filepath = @upload_file.file.current_path
+    stat = File::stat(filepath)
+    send_file(filepath, :filename => @upload_file.file.url.gsub(/.*\//,''), :length => stat.size)
  end

データを1つ以上アップロードした後にRails Consoleを使って見てみると、
モデルの中がどんなオブジェクトになっているのか確認できる。

rails console
> UploadFile
#=> UploadFile(id: integer, name: string, file: string, created_at: datetime, updated_at: datetime)

> UploadFile.first.file.class
#=> UploadFileUploader

> ploadFile.first.file
#=> #<UploadFileUploader:0x007fb75c6fc3e8 @model=#<UploadFile id: 1, name: "hoge", file: "hoge.pdf", created_at: "2015-04-12 17:40:45", updated_at: "2015-04-12 17:40:45">, @mounted_as=:file, @storage=#<CarrierWave::Storage::File:0x007fb75c6fc118 @uploader=#<UploadFileUploader:0x007fb75c6fc3e8 ...>>, @file=#<CarrierWave::SanitizedFile:0x007fb75ba16ca0 @file="/Users/user_name/app_name/public/uploads/upload_file/file/1/hoge.pdf", @original_filename=nil, @content_type=nil>, @versions={}>

参考文献

ライセンス

こちらのコードはMITライセンスです。

sanryuu
Why not register and get more from Qiita?
  1. We will deliver articles that match you
    By following users and tags, you can catch up information on technical fields that you are interested in as a whole
  2. you can read useful information later efficiently
    By "stocking" the articles you like, you can search right away
Comments
No comments
Sign up for free and join this conversation.
If you already have a Qiita account
Why do not you register as a user and use Qiita more conveniently?
You need to log in to use this function. Qiita can be used more conveniently after logging in.
You seem to be reading articles frequently this month. Qiita can be used more conveniently after logging in.
  1. We will deliver articles that match you
    By following users and tags, you can catch up information on technical fields that you are interested in as a whole
  2. you can read useful information later efficiently
    By "stocking" the articles you like, you can search right away
ユーザーは見つかりませんでした