放浪エンジニアのLog

少しハッピーになれる開発

Google 検索結果のスクレイピング

今回はRubyのプログラムで、google検索の検索結果のスクレイピングをやってみようと思います。

主に取得する情報は
URL
タイトル部
スニペット

(スニペット部分は簡単に言うと、下の赤い箇所です!) f:id:kno75:20170220110355p:plain

そもそもスクレイピングとは?

スクレイピングは色んな人が扱っているため、今更説明する必要はないかもしれませんが…

ウェブスクレイピング(英: Web scraping)とは、ウェブサイトから情報を抽出するコンピュータソフトウェア技術のこと。ウェブ・クローラー[1]あるいはウェブ・スパイダー[2]とも呼ばれる。

引用:ウェブスクレイピング - Wikipedia

まさにスクレイピングとは、↑のことです

ざっくりとしたイメージ

例えば「最近の流行りのダイエット」について知りたい!
果たして、他の人はどんなことをWeb上に公開しているのでしょうか? それはダイエットについての「方法」、「効果」、「商品」などなど様々な情報だと思います。
「最近の流行りのダイエット」という漠然としたキーワードでgoogle先生に検索をかけ、ランキング上位の結果を取得し、眺めたり分析やら何やらに使えるのではないでしょうか?

簡単にキーワードからトレンド取得をしたい!
google先生の検索結果の取得がしてみたい!!そんなノリで作りました。

処置の流れ

処理の流れはざっくり分けて、2 stepで行えます。
1. Mechanizeを使って、google先生に検索をかける
2. 検索結果のHTMLから必要な部分を抽出する

ざっくり書くとこんな感じです。 とても簡単ですね….

1. Mechanizeを使って、google先生を使って検索をかける

今回google先生の検索には、Mechanizeを使います。

gemの設定

gem 'mechanize'

とりあえず、google先生に検索をかける箇所を簡単に実装してみる

googleSearch.rb

1 require 'mechanize' 
2                         
3 class GoogleSearch
4   def snipet_scraping(keyword)
5     submit_keyword(keyword)
6   end
7 
8   private
9 
10   def submit_keyword(keyword)
11     agent = Mechanize.new   
12     agent.get('https://www.google.co.jp/')
13     agent.page.form_with(name: 'f') do |form|
14       form.q = keyword
15     end.submit
16   end
17 end
18 
19 result = GoogleSearch.new.snipet_scraping("最近の流行りのダイエット")
20 p result

簡単にmechanizeの解説です
・11〜12行目
Mechanizeのインスタンスを生成し、googleURIをセットしています。

・13〜15行目
google TOPから検索をかける時と同じ容量で作業すると思ってください。
inputボックスの form の name が “f” なので、まずはそれを設定してあげます。

agent.page.form_with(name: 'f')  

次に input box に検索キーワードの設定をするわけですが、input box の name は “q” です。

form.q = keyword

最後に15行目でサブミットして完了です。簡単ですね。

f:id:kno75:20170220153148p:plain

実行結果

$ruby googleSearch.rb

左が実際にgoogle先生に検索をかけた画像で、右がmechanizeを使って実行して得られた結果です。 f:id:kno75:20170220145819p:plain

googleSearch.rb の実行結果では、ページの全HTMLの情報が取得されているので、次のstepで必要な情報だけを取得していきます。

2. 検索結果がHTMLで返ってくるので、必要な部分を抽出する

とりあえずソースを先に貼って、その後解説していきましょう
googleSearch.rb

1  require 'mechanize' 
2                         
3  class GoogleSearch
4    def snipet_scraping(keyword)
5      submit_keyword(keyword)
6      @agent.page.search('div.g').map do |node|
7        title = node.search('a')
8        next if title.empty?
9        query = URI.decode_www_form(URI(title.attr("href")).query)
10       url = query[0][1]
11
12       snipped = node.search('div.s > span.st')
13       next if snipped.empty? || snipped.children.empty?
14       {
15         url: url,
16         title: expect_tag(title.children.to_html),
17         snipped: expect_tag(snipped.children.to_html)
18       }
19     end.reject do |list|
20       list.nil?
21     end
22   end 
23
24   private
25
26   def submit_keyword(keyword)
27      @agent = Mechanize.new   
28      @agent.get('https://www.google.co.jp/')
29      @agent.page.form_with(name: 'f') do |form|
30        form.q = keyword
31      end.submit
32    end
33
34   def expect_tag(str)
35     str.gsub(/(<b>|<\/b>|<br>|<\/br>|\R)/, '')
36   end
37 end
38 
39 result = GoogleSearch.new.snipet_scraping("最近の流行りのダイエット")
40 result.each do |value|
41   p "------------------------------"
42   p "URL     : #{value[:url]}"
43   p "Title   : #{value[:title]}"
44   p "Snipped : #{value[:snipped]}"
45 end

それでは解説していきましょ〜

・6行目

@agent.page.search('div.g').map do |node|  

「div.g」でsearchを行いループを回していますが、これはgoogle先生の1件の検索結果ごとにループを回すようにしています。
また、Mechanizeのsearchを行うと、結果がNokogiriのオブジェクトで返却されます。

f:id:kno75:20170220174832p:plain

なぜ div.g かって?

それはgoogle先生で検索した結果を、consoleから解読したらそうなりました…
もちろん、google先生が何かの気まぐれで、タグの構成などを変えられたら….  

・7行目

title = node.search('a')

検索結果のタイトル(見出し)部の取得をしています。
ご覧の通り、aタグなのです。

・8行目

next if title.empty?

ここでタイトルの空判定をしているのは、実は[ div.g ]で取得を行うと欲しい検索結果以外の情報も取れるため、それを除外しています。

・16〜17行目

title: expect_tag(title.children.to_html),
snipped: expect_tag(snipped.children.to_html)

ここではタイトル, スニペットの設定を行なっていますが、title, snippedから[ children.to_html.to_html ]を行なって、情報を抜き取っています。

・34〜36行目

def expect_tag(str)
  str.gsub(/(<b>|<\/b>|<br>|<\/br>|\R)/, '')
end

上のchildren.to_html.to_html で取得した情報はHTMLのため、タグが含まれています。
そのため、ここで改行、スペース等の不要なタグを削除しています。

実行結果

$ ruby googleSearch.rb

"------------------------------"
"URL     : http://dietbook.biz/tankisyuutyuudietrankingtop10-4647.html"
"Title   : 短期集中ダイエットにおすすめ!【ランキングTOP10】 | ダイエットブックBIZキャッシュ類似ページオー バーナイトダイエットの効果 ...水分だけダイエットの効果と無理 ..."
"Snipped : 短期集中でダイエットしたい方におすすめのダイエット方法をランキングでご紹介しています。私が選ぶダイエット方法T... ... 美容にも良く、ダイエット効果もあるので今流行りのダイエットで噂されています。 個人差も あり、1日ですので大幅な変化はありませんが ..."
"------------------------------"
"URL     : http://thylakoid.jp/geinou/"
"Title   : 2016年度版、あの芸能人も痩せたダイエット方法別まとめキャッシュ"
"Snipped : あの芸能人はちょっと前まで太ってたにもかかわらず、もうダイエットに成功しているけど、一体どうやっているんだろう? 芸能人は忙しい中、ダイエットに成功しているけど、どうせお金も時間もかけてるんでしょ? そう 思っている方は非常に多いかと思います。"
"------------------------------"
"URL     : https://allabout.co.jp/gm/gl/4032/"
"Title   : 流行のダイエットでやせる! [特集・ダイエット] All Aboutキャッシュ"
"Snipped : テレビや雑誌、書籍で続々と紹介される新しいダイエット方法の数々。本当に効果があるの?という疑問に迫り ... 流行のダイエットでやせる! テレビや雑誌、書籍で続々と紹介され ... 最近は低体温の人が増えているそうです。体温が低いと代謝が悪くなるので、 ..."
"------------------------------"
"URL     : https://laurier.press/i/E1459215567169"
"Title   : キーワードは\"食べて痩せる\"!? 2016年に流行るダイエットTOP3 ...キャッシュ"
"Snipped : 2016年3月30日 ... ですが、ダイエットを決意してもなかなか思い通りにはいかないもの。 そこで今回は 、株式会社クックパッド ダイエットラボが3月26日に開催した『ビューティーダイエットフェス 』で紹介された2016年に流行りそうなダイエットをご紹介します。"
"------------------------------"
"URL     : http://diet-tv.net/articles/tv-popular-diet"
"Title   : テレビで話題のダイエット特集!流行りに乗り遅れるな! | ヤセルモキャッシュテレビで今話題のダイエ ットって何があ ...スーパーで手に入るあの食材でこん ..."
"Snipped : 2016年8月9日 ... スーパーで簡単に手に入るあの食材や簡単エクササイズ!テレビで話題の血液型別ダイ エット方法で美ボディを目指しましょう!"
"------------------------------"
"URL     : https://matome.naver.jp/odai/2143278518712676001"
"Title   : 最近流行りのダイエットの中でも変わり種ダイエットが色々すごい件 ...キャッシュ"
"Snipped : 最近流行りのダイエットの中でも変わり種ダイエットが色々すごい件. 美の追求が昔より強力になったのか、近年昔からの定番ダイエットの他、色々個性的なダイエット方法が増えてきています。 更新日: 2017年02月08日. moepapaさん ..."
"------------------------------"
"URL     : https://mdpr.jp/diet/detail/1553707"
"Title   : 【2016年ヒット予測/ダイエットトレンド】今年流行のダイエット法は?日本 ...キャッシュ"
"Snipped : ダイエット/モデルプレス=1月3日】2015年もたくさんのダイエット方法が流行し、モデルプレスでもご紹介してきました。では、2016年はどんなダイエット方法が来るのでしょうか?もう既にジワジワ来ているものもあるよ うですね。そこで今回は、2016年に ..."
"------------------------------"
"URL     : http://one-more-value.com/%E3%83%80%E3%82%A4%E3%82%A8%E3%83%83%E3%83%88-%E6%9C%80%E6%96%B0-2015-%E6%96%B9%E6%B3%95/"
"Title   : 2016年ダイエットを決意したアナタが必ず結果を出す3つの最新方法 ...キャッシュ類似ページ"
"Snipped : ハリウッド女優が実践する5対2ダイエットとは? 『5対2』って何だと思います? 5+2=7なので勘の良い 人は気付いたかもしれませんが、 1週間(7日間)を5日と2日に分けるダイエット手法なのです。 実はコレ、 2012年(3年前に)ロンドンで大流行したダイエット法 ..."
"------------------------------"
"URL     : http://www.womaninsight.jp/archives/202545"
"Title   : 2016年春夏はコレで痩せる!流行ダイエットベスト3を発表 - Woman ...キャッシュ"
"Snipped : 2016年4月4日 ... 今年こそダイエットするぞと意気込んでいる人も、年中ダイエッターの人も、必見! 「クックパッド ダイエットラボ」から、『2016年春夏のダイエット流行予測』が発表になりました。さて、今年はどんなダイエットが人気になるのでしょうか。さっそく ..."
"------------------------------"
"URL     : https://sportsclub.nifty.com/ft_diet/ranking/"
"Title   : 人気ダイエットランキング | @niftyスポーツクラブキャッシュ"
"Snipped : 2016年9月1日 ... いま注目のダイエットや隠れた話題のダイエットを、口コミ件数や評価をもとにランキ ングしてご紹介しています。人気のダイエットをお見逃しなく!"

実際にgoogle先生で検索した結果と全く同じものが取得できました。
これをAPI形式にするか、gemにしても良さそうですね〜

注意事項

本プログラムを使って、スクリプトなどに組み込んで自動的にアクセスを行うことは推奨しておりません! 理由は簡潔言うと一定期間の間にgoogle先生に多量アクセスを行うと、googleへのアタックとみなされ、ブロックされますので、多用は禁物です。
今回は技術的な検証として記事をあげたため、SEO対策などの活用目的としては推奨しておりません。