Ruby on RailsでBULK INSERT
やりたいこと
RailsでBULK INSERTしたい。
方法
Gem「activerecord-import」を使う。
- activerecord-importインストール。
$ vi Gemfile gem 'activerecord-import' $ sudo bundle install
- importメソッドを使用してBULK INSERT
reg_tweets = [] tweets.each do |tweet| # DB登録項目 user = tweet['user'] tweet_id = tweet['id_str'] name = user['name'] screen_name = user['screen_name'] text = tweet['text'] profile_image_url = user['profile_image_url'] tweeted_at = Time.parse(tweet['created_at']) reg_tweets << Tweet.new( :tweet_id => tweet_id, :screen_name => screen_name, :name => name, :text => text, :profile_image_url => profile_image_url, :tweeted_at => tweeted_at, :chapter_id => @chapter_id ) end # BULK INSERT実行 Tweets.import(reg_tweets)
速度検証(軽〜くだけど)
- なお、BULK INSERTとDBドライバを直接使用した場合の速度は下記の通り。
DBドライバ直接使用の方が速い。
■DBドライバ直接使用 [2013/07/16 17:10:27.895040] (pid=7986) INFO -- : AnimeTweetsRegister#register_tweets start [2013/07/16 17:11:25.173947] (pid=7986) INFO -- : 合計登録ツイート数:[25615] [2013/07/16 17:11:25.174424] (pid=7986) INFO -- : AnimeTweetsRegister#register_tweets end ■BULK INSERT使用 [2013/07/16 18:05:18.457076] (pid=9073) INFO -- : AnimeTweetsRegister#register_tweets start [2013/07/16 18:07:01.408476] (pid=9073) INFO -- : 合計登録ツイート数:[25624] [2013/07/16 18:07:01.411327] (pid=9073) INFO -- : AnimeTweetsRegister#register_tweets end
- 全パターンは計測してないけど、一般的には下記の順で速いと思われる。
DBドライバ直接使用 > BULK INSERT > createメソッド
その他
- ちなみに、DBがMySQLの場合はBULK INSERTを行う際にPKが重複してた場合にUPDATEを行う
「ON DUPLICATE KEY UPDATE」が働くとのでPK制約違反発生で登録できないとか無くせるみたい。便利。