rubyからpostgresqlにアクセスする。

rubypostgresqlを使いたかったんです。
Ruby 逆引きレシピ すぐに美味しいサンプル&テクニック 232 (PROGRAMMER’S RECIPE)を読んでみると、
ruby-pgライブラリを使えば接続できるみたいなんで、インストールした。

$ gem install pg

基本的な操作

以下の通り。

#!/opt/local/bin/ruby

require "rubygems"
require "pg"

begin
  conn = PGconn.connect('localhost',5432,'','','test_db','rdera','')
  q    = "select * from hoge_table"
  res  = conn.exec(q)
  res.each do |r|
    p r
  end
rescue PGError => ex
  # PGError process
  print(ex.class," -> ",ex.message)
rescue => ex
  # Other Error  process
  print(ex.class," -> ",ex.message)
ensure
  conn.close if conn
end

データベーステーブルの内容は以下の通り。

test_db=> select * from hoge_table;
 ID | NAME 
----+------
  0 | a
  1 | b

実行結果

{"NAME"=>"a", "ID"=>"0"}
{"NAME"=>"b", "ID"=>"1"}

ちょっと説明してみる

まず、ruby-pgライブラリを使用するためにrubygemsとpgを
requireする必要がある。

require "rubygems"
require "pg"


次に、データベースに接続するためにPGconnのクラスメソッドconnectに
引数を与える。connectメソッドの引数と意味は以下の通り。

http://old.postgresql.jp/interfaces/ruby/reference-ja.html参照

connect(pghost, pgport, pgoptions, pgtty, dbname, login, passwd)
引数 意味
pghost サーバのホスト名(文字列)
pgport サーバがlistenしているポート番号(整数)
pgoptions backendを起動する際に使用するオプション(文字列)
pgtty backendがデバッグメッセージを表示するtty(文字列)
dbname 接続するデータベース名(文字列)
login ユーザ名(文字列)
passwd パスワード(文字列)

失敗した場合は PGError 例外が発生します。

PGconn.connect('localhost',5432,'','','test_db','ri4u','')

このように適宜、省略も可能。


そして、メソッドexecでクエリを実行。

q    = "select * from hoge_table"
res  = conn.exec(q)

http://old.postgresql.jp/interfaces/ruby/reference-ja.html参照
exec(sql)
sqlで指定されたSQL問い合わせ文をPostgreSQLへ送ります。問い合わせが成功した場合には、結果がPGresultクラスのインスタンスとして返され、そうでない場合は例外が発生します。

で……

クラスPGconnはどれだけのメソッドが実装されているのか。

PGconn.instance_methods(false).sort.each do
=>
async_exec:async_query:backend_pid:block:cancel:close:conndefaults:connect_poll:connection_needs_password:connection_used_password:consume_input:db:describe_portal:describe_prepared:error_message:escape:escape_bytea:escape_string:exec:exec_prepared:finish:flush:get_client_encoding:get_copy_data:get_last_result:get_result:host:is_busy:isnonblocking:lo_close:lo_creat:lo_create:lo_export:lo_import:lo_lseek:lo_open:lo_read:lo_seek:lo_tell:lo_truncate:lo_unlink:lo_write:loclose:locreat:locreate:loexport:loimport:lolseek:loopen:loread:loseek:lotell:lotruncate:lounlink:lowrite:make_empty_pgresult:nonblocking?:notifies:notifies_wait:options:parameter_status:pass:port:prepare:protocol_version:put_copy_data:put_copy_end:query:quote_ident:reset:reset_poll:reset_start:send_describe_portal:send_describe_prepared:send_prepare:send_query:send_query_prepared:server_version:set_client_encoding:set_error_verbosity:set_notice_processor:set_notice_receiver:setnonblocking:socket:status:trace:transaction:transaction_status:tty:unescape_bytea:untrace:user:wait_for_notify:

93メソッドですか〜
まとめて調べるのは大変そうなので、適宜調べていきたい。

追記

ruby-pgはC言語のアプリケーションプログラマ用のインタフェースであるlibpq(りぶぴーきゅー?)
を実装しているので、第34章 libpq - C ライブラリ
読んでおくと良いみたい。