2

FasterCSV を使用して Ruby アプリにデータをインポートし、それを SQLite または MySQL データベースに保存する方法を示すチュートリアルを知っている人はいますか?

具体的な手順は次のとおりです。

  1. ファイルを1行ずつ読み取る(.foreachメソッドはドキュメントに従ってこれを行います)
  2. ファイル内のヘッダー名をデータベースの列名にマッピングする
  3. .newCSV データのデータベースにエントリを作成する (ブロック内およびブロック.save内で実行可能と思われる.foreach)

これは基本的な使用シナリオですが、チュートリアルを見つけることができなかったので、リソースがあれば役に立ちます。

ありがとう!

4

4 に答える 4

2

FasterCSV は Ruby 1.9 の時点で Ruby コアの一部になっているようです。上記の質問の目標を達成するために、これが私が最終的に行ったことです。

@importedfile = Import.find(params[:id])
filename = @importedfile.csv.path
CSV.foreach(filename, {:headers => true}) do |row|
  @post = Post.find_or_create_by_email(
    :content          =>  row[0],
    :name             =>  row[1],
    :blog_url         =>  row[2],
    :email            =>  row[3]
  )
end
flash[:notice] = "New posts were successfully processed."
redirect_to posts_path

関数内にfind_or_create_by_emailは、データベース列から CSV ファイルの列へのマッピングがあります: row[0], row[1], row[2], row[3].

これは関数であるため、エントリをデータベースに保存するためfind_or_createに明示的に呼び出す必要はありません。@post.save

より良い方法がある場合は、独自の回答を更新または追加してください。

于 2011-06-05T15:29:58.503 に答える
0

ID を使用してレコードを識別でき、列名のマッピングが必要ない場合、これが最短の方法のようです。

CSV.foreach(filename, {:headers => true}) do |row|
  post = Post.find_or_create_by_id row["id"]
  post.update_attributes row.to_hash
end
于 2012-07-13T13:56:31.790 に答える
0

Ruby は、独自のインポート ルーチンを展開するのに最適です。

  1. ファイルの読み取り (ファイル ハンドルが適切に閉じられるようにするための便利なブロック構造):

    File.open( filepath ) do |f|
      f.each_line do |line|
        do something with the line...
      end
    end
    
  2. ヘッダー名を列にマッピングします (配列の長さが一致するかどうかを確認することをお勧めします):

    Hash[header_array.zip( line_array )]
    
  3. activerecord を使用してデータベースにエントリを作成する:

    SomeModel.create( Hash[header_array.zip( line_array )] )
    

ユーザーがcsvファイルをアップロードしてデータベースにインポートできるようにすることを計画しているようです。彼らがデータに精通していない限り、これは問題を引き起こしています。インポートの前に物事を簡素化するために、nosql ソリューションを検討することをお勧めします。

于 2011-06-05T16:57:48.133 に答える
0

まず、他のスタック オーバーフローの回答から始めます: Ruby で CSV を読み取るための最良の方法。FasterCSV?

コードの記述に取り掛かる前に、インポートを行う既存のツールがあるかどうかを確認します。mysqlimportを見たいと思うかもしれません。

これは、CSV ヘッダーをデータベースの列にマップする方法を示す簡単な例です。

require "csv"

data = <<EOT
header1, header2, header 3
1, 2, 3
2, 2, 3
3, 2, 3
EOT

header_to_table_columns = {
  'header1'  => 'col1',
  'header2'  => 'col2',
  'header 3' => 'col3'
}

arr_of_arrs = CSV.parse(data)
headers = arr_of_arrs.shift.map{ |i| i.strip }
db_cols = header_to_table_columns.values_at(*headers)
arr_of_arrs.each do |ary|
  # insert into the database using an ORM or by creating insert statements
end
于 2011-06-04T18:20:51.977 に答える