Ruby on Railsを触ってみる ②CSVの取り込み
前回の続きで、ツイートCSVファイルの読み込み機能を実装してみる。 ActiveRecordを使って、DBにツイートを取り込む。
まずはRoutes.rbの修正。例に習いgit diffで編集箇所を見てみる。 初めて使ったけど、これは便利だな。
$ git diff config/routes.rb diff --git a/config/routes.rb b/config/routes.rb index cf7d04d..379330e 100644 --- a/config/routes.rb +++ b/config/routes.rb @@ -1,5 +1,10 @@ Twice::Application.routes.draw do - resources :tweets + resources :tweets do + collection do + get 'import_csv_new' + post 'import_csv' + end + end
import_csv_newとimport_csvというメッソドへのルーティングが追加される。
$ rake routes Prefix Verb URI Pattern Controller#Action import_csv_new_tweets GET /tweets/import_csv_new(.:format) tweets#import_csv_new import_csv_tweets POST /tweets/import_csv(.:format) tweets#import_csv tweets GET /tweets(.:format) tweets#index POST /tweets(.:format) tweets#create new_tweet GET /tweets/new(.:format) tweets#new edit_tweet GET /tweets/:id/edit(.:format) tweets#edit tweet GET /tweets/:id(.:format) tweets#show PATCH /tweets/:id(.:format) tweets#update PUT /tweets/:id(.:format) tweets#update DELETE /tweets/:id(.:format) tweets#destroy
tweets_controller.rbにアクションを追記する。
# GET /tweets/import_csv_new def import_csv_new end # POST /tweets/import_csv def import_csv respond_to do |format| if Tweet.import_csv(params[:csv_file]) format.html { redirect_to tweets_path } format.json { head :no_content } else format.html { redirect_to tweets_path, :notice => "CSVファイルの読み込みに失敗しました。" } format.json { head :no_content } end end end
import_csv_newは取り込み用のフォームを設置する。 import_csvで受け取ったCSVを取り込む処理を行い、処理が終わるとツイート一覧のページに遷移させる。 Views/tweets/配下に、import_csv_newに対応するViewファイルを作成する。
<h1>Import tweets CSV File</h1> <%= form_tag('import_csv', :method => 'post', :multipart => true, :class => 'navbar-form pull-left') do %> <%= file_field_tag(:csv_file) %> <%= submit_tag("CSV Import",:class => 'btn') %> <% end %>
import_csvをTweetモデルに作成する。
/* Models/tweet.rb */ # coding: utf-8 require 'csv' # csv操作を可能にするライブラリ require 'kconv' # 文字コード操作をおこなうライブラリ class Tweet < ActiveRecord::Base def self.import_csv(csv_file) # csvファイルを受け取って文字列にする csv_text = csv_file.read # 読み込む前に古いツイートをすべて削除する。 Tweet.delete_all #文字列をUTF-8に変換 CSV.parse(Kconv.toutf8(csv_text)) do |row| # ヘッダー行を回避するためにtweet_idが数値でない場合は読み飛ばす if row[0] =~ /\d+/ tweet = Tweet.new tweet.tweet_id = row[0] tweet.in_reply_to_status_id = row[1] tweet.in_reply_to_user_id = row[2] tweet.timestamp = row[3] tweet.source = row[4] tweet.text = row[5] tweet.retweeted_status_id = row[6] tweet.retweeted_status_user_id = row[7] tweet.retweeted_status_timestamp = row[8] tweet.expanded_urls = row[9] tweet.save end end return true end end
こんな画面になる。イマイチBootstrapが活用できていないような...
ひとまずアップロードしてみる。 お、遅い。。。 とりあえずこんなかんじで一覧が表示される。
Bootstrapのclassを適用してみる。どうやらこの1万件の全ツイートを表示するのに時間がかかるみたい。
とりあえずここまででコミット。 Add CSV import twata701/twice GitHub