Ruby on Railsでサイズの大きいCSVのストリーミング配信について
データベースにあるデータをいじってからCSVに出力したく、以下を参考に実装しました。
http://qiita.com/yutackall/items/24a4487f629a9106a971
その際、サイズが小さい場合は大丈夫ですが、数千件になると発行されるSQLも多くなり、
ダウンロードの準備ができるまで時間がかかります。
(ダウンロードボタンを押してからSQLの発行が全て終わるまでに30分くらい)
サイズが小さい場合はダウンロードできるのですが、大きい場合はSQLの発行が終わってもブラウザにダウンロードされません。(何も起きない)
クライアントでタイムアウトしているのではないかと思い、以下を参考にストリーミング配信にしよと思い実装しました。
http://qiita.com/regonn/items/76fc256d48e4d77c95ef
そうすると、ダウンロードを押してもSQLが走らなく、空のデータになってしまいます。
どこが問題でしょうか。コードを載せます。また、Apache+Passengerで動かしています。
class OutputController < ApplicationController
def download
self.response.headers["Content-Type"] ||= 'text/csv; charset=Shift_JIS'
self.response.headers["Content-Disposition"] = "attachment;filename=export_#{Time.now.to_i}.csv"
self.response.headers["Content-Transfer-Encoding"] = "binary"
self.response.headers["Last-Modified"] = Time.now.ctime.to_s
@input = Input.find(params[:id])
self.response_body = Enumerator.new do |yielder|
@input.baseurls.find_each do |baseurl|
@baseurls = baseurl
yielder << (render :content_type => 'text/csv')
end
end
end
end
この場合ですと@baseurlsには1000件のデータが入り、それをViewのdownload.csv.rubyに渡して1000件ずつ処理をしたいという感じです。download.csv.rubyでCSV.generateしています。