今からスタート! PHP

第10回データベースへのアクセス[関数編]

PHPでデータベース(DB)にアクセスする方法のうち、今回はDBの種類ごとに用意された関数を用いるものを紹介します。関数とは、ある処理のまとまりを記述したもので、引数(ひきすう)というパラメータを関数に渡した後、戻り値というデータが得られるようになっています。

DBアクセスの手順

DBアクセスは、おおむね以下のような手順で行います。

  1. DBに接続
  2. SQLを実行-必要に応じて実行結果を参照
  3. DBから切断

DBアクセスの種類

DBアクセスには、いくつかの種類があります。それは保存されるデータに対してどのような操作をするかで違いがあります。以下のa.からc.の処理を行うプログラムを更新系、d.の処理を行うプログラムを参照系と呼ぶことがあります。

  • a. 追加-新たなデータを保存する(INSERT文)
  • b. 更新-保存されているデータの内容を変更する(UPDATE文)
  • c. 削除-保存されていたデータを削除する(DELETE文)
  • d. 参照-保存されているデータの一覧を参照する(SELECT文)

  • 更新系と参照系では、実行結果が大きく異なります。更新系では、処理が実行されたデータの数などを得られるオブジェクトが実行結果となります。参照系の実行結果は、条件に応じて検索されたデータの一覧です。

    また、本稿では扱いませんが、a.からd.までの処理をまとめて行うストアドプロシージャ(stored procedure)も、DBアクセスにあたって知っておきたい機能です。これは、DBサーバの中にPHPの関数のようなプログラムが収められたものです。PHPプログラムからプロシージャに引数を渡して実行すると、DBサーバ内で処理が実行され、実行結果が戻り値として得られるというものです。

    たくさんのSQL文をまとめて実行したい時や、PHPプログラムの処理負荷を軽減したい時などにストアドプロシージャは活用できます。

    データベースの構築

    DBアクセスを試みる前に、アクセスの対象となるデータベースを構築しておきます。ここからはPostgreSQL8.3 Windows版の場合で説明します。

    DBアクセスの対象は、DB内に構築されたテーブルです。テーブルは表計算における1つの表のように、複数の列や行を持った構造になっています。ここではid, title, urlという3つの列を持ったbookmarkというテーブルを作成します。

    テーブルを作成するには、CREATE TABLE文をDBに対して実行します。このとき、同じurlが複数登録されないようにしています。また、今回はデータを追加するごとに自動的に番号をつける(採番する)シーケンスを用いますので、CREATE SEQUENCE文も実行しますリスト1⁠。

    リスト1 テーブルbookmarkを作成するためのSQL文(PostgreSQL用)
    CREATE SEQUENCE recid;
    CREATE TABLE bookmark (
      id    INTEGER PRIMARY KEY NOT NULL DEFAULT NEXTVAL( 'recid' ),
      title VARCHAR(100) NOT NULL,
      URL   VARCHAR(200) NOT NULL UNIQUE
    );

    リスト1のようなSQL文は1文ずつ実行するよりも、あらかじめファイルに保存しておいて、"psql -U postgres データベース名 < ファイル名" のように一括して実行すると便利です。なお、postgresの部分はユーザ名というもので、実行環境により異なる場合があります。そのかわり、SQL文に誤りがないかを事前によく確認しておいてください。

    テーブルが作成できたら、DBアクセスを行うPHPプログラムを作成していきましょう。

    1. データベースに接続

    DBアクセスを行う前に、必ずDBへの接続を行います。PHPでは pg_connect がPostgreSQLのDBに接続する関数です。接続の際には、host(DBサーバ⁠⁠、port(アクセス先のポート番号⁠⁠、dbname(データベース名⁠⁠、user(ユーザ名⁠⁠、password(パスワード⁠⁠、の各パラメータが必要です。

    リスト2 データベース接続の例
    // データベースpostgresに接続
    $db = pg_connect( 'host=localhost port=5432 dbname=postgres user=postgres password=postgres' ) or die( '接続できませんでした' );

    戻り値の$dbは、DBアクセス時に用いられます。開発者がその内容を知ることが無くても、$dbを使ったDBアクセスは可能です。

    2.SQLの実行

    データの追加

    次にSQLを実行します。リスト1を実行した段階では、まだデータが保存されていません。そこで、テーブルbookmarkにデータを追加します。このとき、追加するデータの文字コードをデータベースが対応するものに変換してください。

    データを追加する時には、pg_prepareによってINSERT文を準備し、その後pg_executeで追加するデータを設定してSQL文を実行するようにします。SQL文は単なる文字列に過ぎませんが、単に文字列をつなげるだけだと、悪意のあるユーザによってSQLインジェクションという不正なアクセスを許してしまう恐れがあるためです。

    リスト3 データの追加
    // 文字コード変換
    $title = mb_convert_encoding( '技術評論社', 'UTF-8', 'SJIS' );
    $url   = mb_convert_encoding( 'http://www.gihyo.co.jp/', 'UTF-8', 'SJIS' );
    // SQL文の準備
    $rs = pg_prepare( $db, 'insert', 'INSERT INTO bookmark( title, url ) VALUES ( $1, $2 )' );
    // データ追加
    $rs = pg_execute( $db, 'insert', array( $title, $url ) );
    // 追加されたデータの数を表示
    print pg_affected_rows( $rs ) .'件のデータを追加しました' . "\n";
    // 実行結果に関するデータを解放(クリア)する
    pg_free_result( $rs );

    追加されたデータの参照

    データを追加できたら、それを参照してみます。参照では、まずSQL文を実行した後、結果として得られた一覧表の各行を順に読み込んでいきます。すべての行を一括して読み込む関数もありますが、メモリ容量や処理負荷の問題を考慮したうえで行ってください。

    なお、このときも文字コードには注意してください。DBが対応する文字コードと表示用の文字コードとが食い違っていると、文字化けの原因になるからです。

    リスト4 データの参照
    // 追加された行を参照
    $rs = pg_query( 'SELECT * FROM bookmark' );
    // 参照可能な行数を表示(正常に実行できたら1)
    print pg_num_rows( $rs ) . '件のデータがあります' . "\n";
    // 1行ずつ読み込み
    while( $row = pg_fetch_array( $rs ) )  {
      // 文字コード変換
      $title = mb_convert_encoding( $row[ 'title' ], 'SJIS', 'UTF-8' );
      // 追加されたデータを表示
      print $title . ' : ' . $row[ 'url' ] . "\n";
    }

    3.DBを切断

    DBアクセスをすべて終了する時は、pg_closeによってそれまで接続していたDBを切断します。これ以降はDBアクセスを実行できません。

    リスト5 DBを切断
    // DBを切断
    pg_close( $db );

    上記1~3までを実行した結果、リスト6のように表示されれば、すべてが正常に実行できたことになります。

    リスト6 1.~3.の実行結果
    1件のデータを追加しました
    1件のデータがあります
    技術評論社 : http://www.gihyo.co.jp/

    関数のおさらい

    今回DB接続からDB切断までに用いた関数の一覧を表1に示します。PostgreSQLにアクセスする関数は、名称の先頭がすべてpg_であることがわかります。このように関数名は、どの種類のDBに対してアクセスを行うものなのかを知る手がかりになります。

    関数の詳細は、PHPマニュアルなどを参照してください。

    表1 今回用いた関数
    pg_connectPostgreSQLのDBに接続する
    pg_prepare 実行するSQLを準備する
    pg_execute 準備したSQLを実行する
    pg_affected_rows 処理が実行された行数を得る
    pg_free_result 実行結果に関するデータを解放(クリア)する
    pg_query SQLをすぐに実行する
    pg_num_rows 参照可能な行数を得る
    pg_fetch_array 1行ずつ参照する
    pg_close 接続していたDBを切断する

    おすすめ記事

    記事・ニュース一覧