Rubyでスクレイピングを試みてますが、全くうまく行きません
50時間試行錯誤しましたが全くうまくいきませんでした。
様々なサイトを見ましたが全く理解できません。
https://vsanna.me/2015/01/26/scraping_start_up/
例えばこのサイトにあるコードをそのまま貼り付けて実行しましたが、何も表示されません。
Ruby on rails で開発したいのですが、XXX.rbのファイルをどこに置けばいいのかも分かりません。
私がやろうとしていることはhttps://www.gakkou.net/chugaku/src/?srcmode=pref&p=2このサイトの各学校のデータ(番号や住所含む)をデータベースに流し込み、ビューで表示することです。そしてそれぞれにリンクを貼って各学校のページに飛びたいです。
どなたか助けてください。。。
気になる質問をクリップする
クリップした質問は、後からいつでもMYページで確認できます。
またクリップした質問に回答があった際、通知やメールを受け取ることができます。
バッドをするには、ログインかつ
こちらの条件を満たす必要があります。
回答2件
0
ベストアンサー
苦労されているようなので、ヒントというか大枠だけ示します。
スクレイピングの前段階として必要な知識が抜けているように思います。
スクレイピングは高度な技術なので、基本的なプログラミングのレベルは必要となります。
また、Rubyを使うのでRubyの文法についてもきちんと知っておかないとけないです。
さらにRailsの知識も必要なので、いきなりスクレイピングだけやりたいというのは実は無理なのです。
それでも、あえて教えるとするとこういう感じかなというのを書きます。
もちろん全部は教えられないので、あくまでも導入部分だけです。
HTTPアクセスをする方法を知る
まず、スクレイピングの前にHTTPアクセスをするためのライブラリが必要です。
個人的にはhttpclientをおすすめします。
Gemfileにgem 'httpclient'
を追記し、ターミナルでbundle installを実行します。
まずは、このhttpclientを使って任意のURLのHTMLを取得できなければいけません。
例えば、こんな感じのメソッドを作って、get_html("http://www.yahoo.co.jp/")
という感じに使います。
相手サイト、サーバに負荷をかけないように簡易的なキャッシュ機能を入れます。
rubyではエンコーディングが正しくないと例外で落ちるので、キャッシュファイルの入出力のエンコーディングはbinaryとしておきます。
ruby
1def get_html(url) 2 client = HTTPClient.new 3 client.connect_timeout = 10 4 client.send_timeout = 10 5 client.receive_timeout = 30 6 7 cache_id = Digest::SHA1.hexdigest(url) 8 cache_path = "#{Rails.root}/tmp/cache/response/#{cache_id}" 9 FileUtils.mkdir_p(File.dirname(cache_path), mode: 0771) 10 11 # using cache 12 if File.exist?(cache_path) 13 Rails.logger.debug "using cache: url=#{url}" 14 return File.read(cache_path, encoding: 'binary') 15 end 16 17 response = client.get(url, :follow_redirect => true) 18 unless response.status == 200 19 raise "request failed: #{response.inspect}" 20 end 21 22 # no cache 23 Rails.logger.debug "no cache: url=#{url}" 24 File.open(cache_path, 'w:binary'){|f| 25 f.print response.body 26 } 27 28 response.body 29end
どこに置くのか
とりあえずapp/以下であれば自動で読み込み対象となります。
デフォルトでそういう設定になっているはずなので。
良く分からなければ、app/models/crawl.rbというのを作りましょう。
DBと関係なくても、モデルと呼ぶ場合もあるし問題ないかと。
ruby
1class Crawl 2 3 def get_html(url) 4 client = HTTPClient.new 5 client.connect_timeout = 10 6 client.send_timeout = 10 7 client.receive_timeout = 30 8 9 cache_id = Digest::SHA1.hexdigest(url) 10 cache_path = "#{Rails.root}/tmp/cache/response/#{cache_id}" 11 FileUtils.mkdir_p(File.dirname(cache_path), mode: 0771) 12 13 # using cache 14 if File.exist?(cache_path) 15 Rails.logger.debug "using cache: url=#{url}" 16 return File.read(cache_path, encoding: 'binary') 17 end 18 19 response = client.get(url, :follow_redirect => true) 20 unless response.status == 200 21 raise "request failed: #{response.inspect}" 22 end 23 24 # no cache 25 Rails.logger.debug "no cache: url=#{url}" 26 File.open(cache_path, 'w:binary'){|f| 27 f.print response.body 28 } 29 30 response.body 31 end 32 33end
実行方法は2つあります。
まず、rails consoleを実行する方法。
$ rails console > Crawl.new.get_html("http://www.yahoo.co.jp/") ...
次に、rails runnerを使う方法。
この場合、画面に何も出ないので、Crawlのコードの中でputsなどを入れてください。
$ rails runner 'Crawl.new.get_html("http://www.yahoo.co.jp/")'
Nokogiriを使ってみる
ここまでで、とりあえず任意のURLのHTMLを取れるようになりました。
ようやくスクレイピングです。
例えば、 https://www.gakkou.net/chugaku/src/?srcmode=pref&p=13 を例にします。
- ブラウザでhttps://www.gakkou.net/chugaku/src/?srcmode=pref&p=13にアクセス
- ブラウザのソースを表示で、HTMLを確認する
- 取得したい部分のHTML構造を把握する
今回の例では、学校名を取りたいと思います。
とりあえず、ソースをながめてdiv.UvsinfoBxの直下のh3タグが学校名っぽいし、繰り返しのパターンになっているなという風に考えます。
html
1<div class="UvsinfoBx"> 2<a href="../view/index_204110.html"> 3<h3>愛国中学校</h3> 4</a>
これについては、試行錯誤して経験を積むしかないので、どこかのサイトを参考にするという事はできません。
色々試しましょう。
この場合、こういう風にコードを組む事になるでしょう。
とりあえず、プロジェクト直下にcrawl_test.rbとしてそのまま保存します。
ruby
1html = Crawl.new.get_html("https://www.gakkou.net/chugaku/src/?srcmode=pref&p=13") 2doc = Nokogiri::parse(html) 3doc.css('div.UvsinfoBx').each do |div| 4 puts div.css('h3').first.text.to_s 5end
そして、実行するとこういう感じに出力されます。
$ rails runner ./crawl_test.rb 愛国中学校 青ケ島村立青ケ島中学校 青山学院中等部 ...
以上が、基本的なスクレイピングの流れです。
スクレイピング対象のページごとにHTML構造が違うので、取得コードを変える必要がありますし、
URLの一覧を取得する処理も必要です。
この点については、さすがに手取り足取りというわけにはいかないので工夫してみてください。
投稿2017/12/05 12:37
総合スコア4025
あなたの回答
tips
太字
斜体
打ち消し線
見出し
引用テキストの挿入
コードの挿入
リンクの挿入
リストの挿入
番号リストの挿入
表の挿入
水平線の挿入
プレビュー
質問の解決につながる回答をしましょう。 サンプルコードなど、より具体的な説明があると質問者の理解の助けになります。 また、読む側のことを考えた、分かりやすい文章を心がけましょう。
バッドをするには、ログインかつ
こちらの条件を満たす必要があります。
2017/12/05 18:08
2017/12/05 18:11
2017/12/05 22:42 編集
2017/12/06 17:50
2017/12/06 22:14