LoginSignup
363
353

More than 1 year has passed since last update.

RailsでExcelを扱うGemまとめ

Last updated at Posted at 2014-08-24

RailsにはExcelを扱うGemがいくつかあり、それぞれ特徴があるのでまとめてみる。
ついでに簡単なテストコードも載せてみる。

テストで扱うデータはこんな感じ。
もちろんしかるべきところには計算式を入れてある。
新規作成の場合はこれを作成する。
読み込みの場合はこのデータを読み込んで表示、さらに編集・書き出しが可能な場合には牛肉の単価を500円(和牛)に変更する。

品名 単価 数量
にんじん 80 1 80
たまねぎ 50 2 100
じゃがいも 40 2 80
牛肉 200 1 200
カレー粉 150 1 150
610

spreadsheet

zdavatz/spreadsheet

  • TheRubyToolboxによると、一番多く使われているらしい
  • .xlsx, .xlsmは扱えない
  • 新規作成、読み込み、書き出しが可能
  • セルの書式設定は面倒そう
# 新規作成
book = Spreadsheet::Workbook.new                
sheet = book.create_worksheet(name: 'curry')    
                     
# いろいろな方法でデータを入れられる
# 計算式は入力できない                           
sheet.row(0).concat %w{品名 単価 数量 計}       
                                                
sheet[1,0] = 'にんじん'                         
sheet[1,1] = 80                                 
sheet[1,2] = 1                                  
sheet[1,3] = 80                                 
                                                
row = sheet.row(2)                              
row.push 50                                     
row.push 2                                      
row.push 100                                    
row.unshift 'たまねぎ'                          
                                                
sheet.row(3).replace [ 'じゃがいも', 40, 2, 80 ]
                                                
sheet.row(4).push '牛肉', 1, 200                
sheet.row(4).insert 1, 200                      
                                                
sheet.update_row 5, 'カレー粉', 150, 1, 150     
                                                
sheet[6,2] = '総計'                             
sheet[6,3] = 610

book.write('test.xls')                                
# 読み込み                                                                                                   
book = Spreadsheet.open(filepath)                                                                  
sheet = book.worksheet('curry')                                                                              
sheet.each do |row|                                                                                          
    # 数式が入っているセルは .value で値を取得                                                                                  
    puts "#{row[0]} #{row[1]} #{row[2]} #{row[3].instance_of?(Spreadsheet::Formula) ? row[3].value : row[3]}"
end                                                                                                          

axlsx

randym/axlsx

  • 扱う拡張子は.xlsx
  • 新規作成専用で、既存ファイルの読み込みは不可
  • セルの書式設定はやりやすい印象
  • セルに画像を貼ったり、グラフを表示したりもできるっぽい(未検証)
# 新規作成
package = Axlsx::Package.new                             
sheet = package.workbook.add_worksheet(name: 'curry')    

sheet.add_row(['品名', '単価', '数量', '計'])            
sheet.add_row(['にんじん',    80, 1,      '=B2*C2'])     
sheet.add_row(['たまねぎ',    50, 2,      '=B3*C3'])     
sheet.add_row(['じゃがいも',  40, 2,      '=B4*C4'])     
sheet.add_row(['牛肉',       200, 1,      '=B5*C5'])     
sheet.add_row(['カレー粉',   150, 1,      '=B6*C6'])     
sheet.add_row(['',            '', '総計', '=SUM(D2:D6)'])

package.serialize('test.xlsx')                        

roo

Empact/roo

  • .xls.xlsxが扱える(他にも.ods.csvや google spreadsheet も扱えるらしい)
  • 読み込み専用で、新規作成、書き出しは不可
# 読み込み                                                                      
s = Roo::Excel.new(filepath)  # .xlsx を読み込むときは Roo::Excelx.new                                                  
s.default_sheet = 'curry'                                                       
s.first_row.upto(s.last_row) do |row|                                           
  puts "#{s.cell(row, 1)} #{s.cell(row, 2)} #{s.cell(row, 3)} #{s.cell(row, 4)}"
end                                                                             

rubyXL

weshatheleopard/rubyXL

  • .xlsx.xlsmが扱えるが、.xlsmにマクロが含まれているとデータが壊れる…
  • もしマクロ入り.xlsmを壊さずに扱える方法をご存じの方がいれば教えて下さい!
  • 新規作成、読み込み、書き出しが可能
  • セルの書式設定はやりやすい印象
# 新規作成
book = RubyXL::Workbook.new                  
sheet = book[0]   # 最初からシートが1つある 
sheet.sheet_name = 'curry'                   
sheet.add_cell(0, 0, '品名')                 
sheet.add_cell(0, 1, '単価')                 
sheet.add_cell(0, 2, '数量')                 
sheet.add_cell(0, 3, '計')                   
                                             
sheet.add_cell(1, 0, 'にんじん')             
sheet.add_cell(1, 1, 80)                     
sheet.add_cell(1, 2, 1)                      
sheet.add_cell(1, 3, '', 'B2*C2')    

# 中略         
                                             
sheet.add_cell(6, 2, '計')                   
sheet.add_cell(6, 3, '', 'SUM(D2:D6)')       
                                             
book.write("test.xlsx")                   
# 読み込み                                                                
book = RubyXL::Parser.parse(filepath)                                     
sheet = book['curry']                                                     
sheet.each do |row|                                                       
  puts "#{row[0].value} #{row[1].value} #{row[2].value} #{row[3].value}"  
end                                                                       
                                                                          
# 編集                                                                    
sheet[4][1].change_contents(500)                                          
                                                                          
# 書き込み                                                                
book.write(filepath)                                                      

まとめ

使い分けとしては、

  • .xlsでもいいからネット上の情報が豊富なやつを使いたい -> spreadsheet
  • システムのみでリッチな.xlsxファイルを作りたい -> axlsx
  • .xlsxファイルを読み出すだけでいいから気軽に扱いたい -> roo
  • テンプレートの.xlsxファイルがあって、それにデータを書き込んで保存したい -> rubyXL

といった感じかな…。

ちなみにどのGemでもマクロが含まれていると扱えなかった。

363
353
1

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
363
353