11
8

More than 5 years have passed since last update.

【初心者向け】RailsでCSV出力する方法

Posted at

初めに

RailsでCSV出力を実装したので解説します。
今回はUserの名前、メールアドレス、アカウント作成日を出力してみます。

大まかな説明

RailsはModel, View, controllerとありますが、実際にいじるのはviewcontrollerです。

viewではcsvファイルの作成と、出力ボタンを設置します。
controllerはcsvとして出力するオブジェクトを投げてファイル名を設定します。

CSVファイルの作成(View)

viewにcsvファイルを作成するためのファイルを作ります。
xxxx.csv.rubyと拡張子で作成します。

app/view/users/index.csv.ruby
require 'csv'

CSV.generate do |csv|
  csv_column_names = %w(name email created_at)
  csv << csv_column_names
  @users.each do |user|
    column_values = [
      user.name,
      user.email,
      user.created_at
    ]
    csv << column_values
  end
end

csv << column_names で表の列に入る名前を定義します。
csv << column_values で表の行に入る値を定義します。

CSV出力ボタンの設置(View)

app/view/users/index.html.erb
<%= link_to "CSV出力", users_path(format: :csv), class: "btn btn-primary" %>

CSV出力のボタンを設置します。
ここではusersコントローラーのindexアクションで実行するのでusers_pathとしていますが、
rails routesで自分の実行したいアクションのルーティングを調べてから書いてください。
また(format: :csv)と最後につけるのを忘れないようにしてください。

フォーマットごとに出力内容を指定(Controller)

app/controllers/users_controller.rb
class UsersController < ApplicationController
  def index
    @users = User.all
    respond_to do |format|
      format.html do
          #html用の処理を書く
      end 
      format.csv do
          #csv用の処理を書く
          send_data render_to_string, filename: "(ファイル名).csv", type: :csv
      endw
    end
  end
end

フォーマット後のに処理をわけて書きます。
ファイル名を変更したい時は、上記のように
send_data render_to_string, filename: "(ファイル名).csv", type: :csv
と書きます。

リファクタリング

このままでも動くのですがViewでの書き方は改良の余地があります。

app/view/users/index.csv.ruby
require 'csv'

CSV.generate do |csv|
  csv_column_names = %w(name email created_at)
  csv << csv_column_names
  @users.pluck(*csv_column_names).each do |user|
    csv << user
  end
end

このようにすることによって、csv_column_namesの内容が変わっても修正する箇所が少なくて済みます。
また処理がeachだけの時よりもはやいです。

最後に

以上でCSV出力の実装の終わりです。
なにか間違っているところなどあればご指摘ください!

11
8
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
11
8