非常に大きな CSV ファイルをダウンロードして解凍し、1 行ずつ処理する必要があるという問題があります。ファイルの大きさを教えていただけると助かります。
- big_file.zip ~700MB
- big_file.csv ~23GB
ここに私が起こりたいことがいくつかあります:
- 解凍する前にファイル全体をダウンロードする必要はありません
- csv 行を解析する前にファイル全体を解凍する必要はありません
- これらすべてを実行している間、メモリ/ディスクをあまり使い切らないでください
それが可能かどうかはわかりません。これが私が考えていたことです:
require 'open-uri'
require 'rubyzip'
require 'csv'
open('http://foo.bar/big_file.zip') do |zipped|
Zip::InputStream.open(zipped) do |unzipped|
sleep 10 until entry = unzipped.get_next_entry && entry.name == 'big_file.csv'
CSV.foreach(unzipped) do |row|
# process the row, maybe write out to STDOUT or some file
end
end
end
私が知っている問題は次のとおりです。
open-uri
応答全体を読み取り、Tempfile
このサイズのファイルには適していない に保存します。おそらくNet::HTTP
直接使用する必要がありますが、それを行う方法がわかりませんが、IO
.- ダウンロードがどれくらい速くなるか、または
Zip::InputStream
私が示したように機能するかどうかはわかりません. ファイルの一部がまだ解凍されていない場合、ファイルの一部を解凍できますか? - rubyzip で
CSV.foreach
動作しInputStream
ますか?File
行を解析できるように十分に動作しますか? 読みたいのにバッファが空の場合、びっくりしますか?
これが正しいアプローチであるかどうかはわかりません。たぶん、いくつかの EventMachine ソリューションの方が優れているでしょう (ただし、これまで EventMachine を使用したことはありませんが、このようなものでうまく機能する場合は、それで十分です)。