RubyでNokogiriを使ってみる

CentOSにRuby2.1.1をインストールする
の続き

RubyでNokogiriを使ってみる。

【参考】
Ruby製の構文解析ツール、Nokogiriの使い方 with Xpath - プログラマになりたい
http://blog.takuros.net/entry/2014/04/15/070434

インストール

まずは必要なライブラリをいれておく。

$ sudo yum -y install libxml2 libxml2-devel
$ sudo yum -y install libxslt libxslt-devel

Nokogiriをしようとすると、なぜかエラーが出る。

$ sudo gem install nokogiri
Fetching: mini_portile-0.6.0.gem (100%)
Successfully installed mini_portile-0.6.0
Fetching: nokogiri-1.6.3.1.gem (100%)
Building native extensions.  This could take a while...
Building nokogiri using packaged libraries.
Building libxml2-2.8.0 for nokogiri with the following patches applied:
・・・
************************************************************************
IMPORTANT!  Nokogiri builds and uses a packaged version of libxml2.

If this is a concern for you and you want to use the system library
instead, abort this installation process and reinstall nokogiri as
follows:

    gem install nokogiri -- --use-system-libraries

If you are using Bundler, tell it to use the option:

    bundle config build.nokogiri --use-system-libraries
    bundle install

However, note that nokogiri does not necessarily support all versions
of libxml2.

For example, libxml2-2.9.0 and higher are currently known to be broken
and thus unsupported by nokogiri, due to compatibility problems and
XPath optimization bugs.
************************************************************************
ERROR:  Error installing nokogiri:
        ERROR: Failed to build gem native extension.
・・・

よく分からないのでエラーの内容に従って下記のようにインストールしてみる。

$ sudo gem install nokogiri -- --use-system-libraries

入ったっぽい。

$ nokogiri -v
# Nokogiri (1.6.3.1)
・・・

タイトル取得

タイトルを取得してみる。

$ vi sample.rb
require 'nokogiri'

html = <<"EOS"
<!DOCTYPE html>
<html lang="ja">
<head>
  <meta charset="utf-8">
  <title>サンプル</title>
</head>
<body>
</body>
</html>
EOS

doc = Nokogiri::HTML.parse(html)

puts "[タイトル]"
puts doc.title
実行結果
$ ruby sample.rb
[タイトル]
サンプル

各種参照

各種情報を取得してみる。

$ vi sample.rb
require 'nokogiri'

html = <<"EOS"
<!DOCTYPE html>
<html lang="ja">
<head>
  <meta charset="utf-8">
</head>
<body>
  <a href="http://www.yahoo.co.jp"><font color="blue">ヤフー</font></a>
</body>
</html>
EOS

doc = Nokogiri::HTML.parse(html)

puts "[HTML]"
puts doc.css('a').to_s
puts
puts "[タグ内のHTML]"
puts doc.css('a').inner_html
puts
puts "[タグ内のテキスト]"
puts doc.css('a').inner_text
puts
puts "[inner_textのエイリアス]"
puts doc.css('a').text
puts
puts "[属性]"
puts doc.css('a').attribute('href')
実行結果
$ ruby sample.rb
[HTML]
<a href="http://www.yahoo.co.jp"><font color="blue">ヤフー</font></a>

[タグ内のHTML]
<font color="blue">ヤフー</font>

[タグ内のテキスト]
ヤフー

[inner_textのエイリアス]
ヤフー

[属性]
http://www.yahoo.co.jp

各種検索

xpathはよく分かってないので、cssでの検索を試す。

$ vi sample.rb
require 'nokogiri'

html = <<"EOS"
<!DOCTYPE html>
<html lang="ja">
<head>
  <meta charset="utf-8">
</head>
<body>
  <div id="id1" class="classA">div1</div>
  <div id="id2" class="classA">div2</div>
  <div id="id3" class="classA">div3</div>
  <div id="id4" class="classB">div4</div>
  <div id="id5" class="classB">div5</div>
  <div id="id6" class="classB">div6</div>
</body>
</html>
EOS

doc = Nokogiri::HTML.parse(html)

puts "[1件目]"
puts doc.css('div').first.text
puts
puts "[1件目(別パターン)]"
puts doc.at_css('div').text
puts
puts "[複数件]"
doc.css('div').each do |node|
  puts node.text
end
puts
puts "[ID指定]"
puts doc.css('#id1').text
puts
puts "[クラス指定]"
doc.css('.classB').each do |node|
  puts node.text
end
実行結果
$ ruby sample.rb
[1件目]
div1

[1件目(別パターン)]
div1

[複数件]
div1
div2
div3
div4
div5
div6

[ID指定]
div1

[クラス指定]
div4
div5
div6