準備
ビルド
PDO ドライバ How-To
PHP Manual

## 雛形への肉付け

### 主要な構造体および属性

主要な構造体である pdo_dbh_t および pdo_stmt_t については、それぞれ 付録 A および B で説明します。データベースやステートメントの属性に ついては 付録 C、エラー処理については付録 D で説明します。

### pdo_SKEL.c: PHP 拡張モジュールとの橋渡し

#### 関数エントリ

    static function_entry pdo_SKEL_functions[] = {
      { NULL, NULL, NULL }
    };

この構造体は、グローバルな PHP 関数名前空間に関数を登録するために 使用されます。PDO ドライバでは、できるだけ使用を避けるべきです。 上の例で示しているように、NULL で初期化した状態にしておくことを 推奨します。

#### モジュールエントリ

    /* {{{ pdo_SKEL_module_entry */
    #if ZEND_EXTENSION_API_NO >= 220050617
    static zend_module_dep pdo_SKEL_deps[] = {
        ZEND_MOD_REQUIRED("pdo")
        {NULL, NULL, NULL}
    };
    #endif
    /* }}} */

    zend_module_entry pdo_SKEL_module_entry = {
    #if ZEND_EXTENSION_API_NO >= 220050617
        STANDARD_MODULE_HEADER_EX, NULL,
        pdo_SKEL_deps,
    #else
        STANDARD_MODULE_HEADER,
    #endif
        "pdo_SKEL",
        pdo_SKEL_functions,
        PHP_MINIT(pdo_SKEL),
        PHP_MSHUTDOWN(pdo_SKEL),
        NULL,
        NULL,
        PHP_MINFO(pdo_SKEL),
        PHP_PDO_<DB>_MODULE_VERSION,
        STANDARD_MODULE_PROPERTIES
    };
    /* }}} */

    #ifdef COMPILE_DL_PDO_<DB>
    ZEND_GET_MODULE(pdo_db)
    #endif

pdo_SKEL_module_entry という名前で zend_module_entry 型の構造体を宣言し、先ほど定義した pdo_SKEL_functions テーブルへの参照を含める必要があります。

#### 標準 PHP 拡張モジュール関数

##### PHP_MINIT_FUNCTION

    /* {{{ PHP_MINIT_FUNCTION */
    PHP_MINIT_FUNCTION(pdo_SKEL)
    {
        return php_pdo_register_driver(&pdo_SKEL_driver);
    }
    /* }}} */

この標準 PHP 拡張モジュール関数は、ドライバを PDO に登録するために 使用されます。登録するには、php_pdo_register_driver() 関数に pdo_driver_t 型の構造体へのポインタを渡して コールします。この構造体の名前は、一般的には pdo_SKEL_driver となります。 pdo_driver_t には、マクロ PDO_DRIVER_HEADER(SKEL) を使用して生成した ヘッダおよび pdo_SKEL_handle_factory() 関数へのポインタが含まれます。実際の関数については SKEL_dbh.c の説明の中で述べます。

##### PHP_MSHUTDOWN_FUNCTION

    /* {{{ PHP_MSHUTDOWN_FUNCTION */
    PHP_MSHUTDOWN_FUNCTION(pdo_SKEL)
    {
        php_pdo_unregister_driver(&pdo_SKEL_driver);
        return SUCCESS;
    }
    /* }}} */

この標準 PHP 拡張モジュール関数は、ドライバを PDO から登録解除する ために使用されます。解除するには、 php_pdo_unregister_driver() 関数に 上で渡したのと同じ構造体 pdo_SKEL_driver を渡してコールします。

##### PHP_MINFO_FUNCTION

これもまた標準 PHP 拡張モジュール関数です。この関数の目的は、 スクリプト内で phpinfo() がコールされた際に モジュールの情報を表示することです。規約では、モジュールの バージョンおよび対応するデータベースのバージョン、そして 関連する設定情報を表示することになっています。

### SKEL_driver.c: ドライバの実装

このファイルでは、PDO データベースハンドルオブジェクトがサポートする すべてのデータベース処理メソッドを実装します。また、エラー情報の 取得ルーチンもここに含まれます。これらの関数では、グローバル変数 プールへのアクセスが必要になることでしょう。そのため、これらの ステートメントの最後には、Zend マクロ TSRMLS_DC を使用する必要が あります。このマクロについての詳細な情報は、Zend の プログラマ向けドキュメントを参照ください。

#### pdo_SKEL_error

    static int pdo_SKEL_error(pdo_dbh_t *dbh,
      pdo_stmt_t *stmt, const char *file, int line TSRMLS_DC)

この関数の目的は、ドライバ内での一般的なエラー処理関数として使用する ことです。ドライバ内でエラーが発生した場合に、ドライバによって この関数がコールされます。SQLSTATE に関連しないエラーが発生した場合、 ドライバはエラーの内容にもっとも近い SQLSTATE あるいは一般的な SQLSTATE エラー "HY000" を、 dbh->error_code あるいは stmt->error_code にセットする必要があります。 PDO ソース内のファイル pdo_sqlstate.c には、PDO が明示的に理解する 一般的な SQLSTATE コードのテーブルがあります。エラーコードの設定は、 この関数がコールされる前に終わっていなければなりません。この関数は、 グローバル変数 `pdo_err` に dbh あるいは stmt (stmt が NULL でない場合) で見つかったエラーを設定します。

dbh

  ハンドルファクトリで初期化したデータベースハンドルへのポインタ。

stmt

  現在のステートメントへのポインタあるいは NULL。 NULL の場合、エラーには dbh で見つかったエラーコードが設定されます。

file

  エラーが発生したソースファイルあるいは取得できない場合は NULL。

line

  取得可能な場合に、ソースファイル内の行番号。

dbh メンバメソッドが NULL の場合 (PDO コンストラクタ内でエラーが 発生したことを意味します)、この関数は zend_throw_exception_ex() 関数をコールしなければなりません。それ以外の場合はエラーコードを 返します。通常、この関数はヘルパマクロを使用してコールされます。 このマクロは、データベース処理エラーおよびステートメント処理エラーの それぞれについて関数のコール手順をカスタマイズしたものです。

例1 pdo_SKEL_error をコールするマクロの例

    #define pdo_SKEL_drv_error(what) \
        pdo_SKEL_error(dbh, NULL, what, __FILE__, __LINE__ TSRMLS_CC)
    #define pdo_SKEL_drv_error(what) \
        pdo_SKEL_error(dbh, NULL, what, __FILE__, __LINE__ TSRMLS_CC)

エラー処理についての詳細は、エラー処理 を参照ください。

> 注意: このように記述されていますが、PDO ドライバインターフェイスでは特に この関数が存在することを指定していません。これは単にエラー処理を 便利にするための方法であり、大半のデータベースのクライアントライブラリ API ではこの方法でドライバを実装すると好都合です。

#### pdo_SKEL_fetch_error_func

    static int pdo_SKEL_fetch_error_func(pdo_dbh_t *dbh, pdo_stmt_t *stmt,
        zval *info TSRMLS_DC)

この関数の目的は、直近に発生したエラーについての追加情報を 取得することです。ここには、ドライバ固有のエラーコードや 人間が理解できる形式のメッセージが含まれます。また、必要に応じて それ以外の追加情報も含められます。この関数は、PHP スクリプトで PDO::errorInfo() メソッドをコールした際に 呼び出されます。

dbh

  ハンドルファクトリで初期化したデータベースハンドルへのポインタ。

stmt

  現在のステートメントへのポインタあるいは NULL。NULL の場合は dbh で見つかったエラーコードから情報を取得します。

info

  エラーコードおよびメッセージを含むハッシュテーブル。

error_func は、情報を 2 つの部分に分けた上で、配列の連続する要素として 返さなければなりません。最初の要素は数値形式のエラーコードで、次の 項目が文字列の説明となります。この項目を設定する方法としては add_next_index を使用するのが最適です。最初の要素の型は long である必要がないことに注意しましょう。元になるデータベース API が返すエラーコードに応じた型を選びます。

    /* ここではエラー情報を追加します。 */
    /* 指定した順に追加する必要があります。 */
    add_next_index_long(info, error_code);   /* ドライバ固有のエラーコード */
    add_next_index_string(info, message, 0); /* 可読形式のエラーメッセージ */

この関数は、情報が取得可能な場合に 1、ドライバが追加情報を 保持していない場合に 0 を返します。

#### SKEL_handle_closer

    static int SKEL_handle_closer(pdo_dbh_t *dbh TSRMLS_DC)

この関数は、オープンしているデータベースを閉じるために PDO からコールされます。

dbh

  ハンドルファクトリで初期化したデータベースハンドルへのポインタ。

オープン中のデータベースを閉じるために必要な処理は、すべてここで 済ませる必要があります。PDO は、この関数の返す値を無視します。

#### SKEL_handle_preparer

    static int SKEL_handle_preparer(pdo_dbh_t *dbh, const char *sql,
    long sql_len, pdo_stmt_t *stmt, zval *driver_options TSRMLS_DC)

この関数は、PHP スクリプトで PDO::query() および PDO::prepare() がコールされた場合に PDO から呼び出されます。この関数の目的は、 実行する SQL を準備し、渡された `stmt` に しかるべき値を格納することです。

dbh

  ハンドルファクトリで初期化したデータベースハンドルへのポインタ。

sql

  準備される SQL ステートメントを含む文字列へのポインタ。

sql_len

  SQL ステートメントの長さ。

Stmt

  返される statement へのポインタか、エラーが発生した場合には NULL。

driver_options

  ドライバ固有の (ドライバで定義した) オプション。

この関数は、本質的には stmt オブジェクトのコンストラクタです。 ステートメントのオプションを処理し、ドライバ固有のオプションを pdo_stmt_t 構造体に格納することがこの関数の役割となります。

prepare 関数がコールされる前に、PDO がドライバの代わりにオプションを 処理してくれることはありません。未知のオプションが渡された際に エラーを発生させるなどの処理は、あなた (ドライバ) の役割となります。

この関数の非常に重要な役割のひとつは、SQL ステートメントのパラメータを 処理することです。この関数をコールした際に、PDO は 「ドライバがプリペアドステートメントへのパラメータのバインドをサポート しているか」や「名前で指定するパラメータあるいは位置で指定するパラメータの どちらをサポートしているか」を知りません。

元となるデータベースにあわせて、ドライバが適切に stmt->supports_placeholders を設定しなければなりません。 接続先のサーバのバージョンによってこの設定が変化するなどの理由で、 この設定を実行時に行わなければならないこともあるかもしれません。 ドライバが、名前で指定するパラメータ・位置で指定するパラメータのいすれも サポートしていない場合は、pdo_parse_params() API を使用して PDO にクエリを書き換えさせることでこの機能を サポートさせなければなりません。

例2 pdo_parse_params の使用

    int ret;
        char *nsql = NULL;
        int nsql_len = 0;

        /* クエリを準備する前に、ちょっとその中身を確かめる必要があります。
         * もし名前で指定するパラメータが用いられていれば、その処理を
         * PDO に任せます */
        stmt->supports_placeholders = PDO_PLACEHOLDER_POSITIONAL;
        ret = pdo_parse_params(stmt, (char*)sql, sql_len, &nsql, &nsql_len TSRMLS_CC);

        if (ret == 1) {
            /* クエリが書き換えられました */
            sql = nsql;
        } else if (ret == -1) {
            /* 失敗しました */
            strcpy(dbh->error_code, stmt->error_code);
            return 0;
        }

        /* "sql" の中のクエリを準備します */

supports_placeholders に指定できる値は `PDO_PLACEHOLDER_NAMED`、 `PDO_PLACEHOLDER_POSITIONAL` および `PDO_PLACEHOLDER_NONE` です。 ドライバがプリペアドステートメントをまったくサポートしていない場合、 この関数は単に必要なデータを割り当てたうえで、それを返す必要があります。

例3 プリペアドステートメントをネイティブにサポートしていないドライバでの実装

    static int SKEL_handle_preparer(pdo_dbh_t *dbh, const char *sql,
        long sql_len, pdo_stmt_t *stmt, zval *driver_options TSRMLS_DC)
    {
        pdo_SKEL_db_handle *H = (pdo_SKEL_db_handle *)dbh->driver_data;
        pdo_SKEL_stmt *S = ecalloc(1, sizeof(pdo_SKEL_stmt));

        S->H = H;
        stmt->driver_data = S;
        stmt->methods = &SKEL_stmt_methods;
        stmt->supports_placeholders = PDO_PLACEHOLDER_NONE;

        return 1;
    }

この関数は、成功した場合に 1、失敗した場合に 0 を返します。

#### SKEL_handle_doer

    static long SKEL_handle_doer(pdo_dbh_t *dbh, const char *sql, long sql_len TSRMLS_DC)

この関数は、SQL ステートメントを直接実行する際に PDO から 呼び出されます。pdo_stmt_t は作成されません。

dbh

  ハンドルファクトリで初期化したデータベースハンドルへのポインタ。

sql

  準備される SQL ステートメントを含む文字列へのポインタ。

sql_len

  SQL ステートメントの長さ。

この関数は、成功した場合に 1、失敗した場合に 0 を返します。

#### SKEL_handle_quoter

    static int SKEL_handle_quoter(pdo_dbh_t *dbh, const char *unquoted,
      int unquoted_len, char **quoted, int quoted_len, enum pdo_param_type param_type TSRMLS_DC)

この関数は、クエリで使用するために文字列をクォートする際に PDO から呼び出されます。

dbh

  ハンドルファクトリで初期化したデータベースハンドルへのポインタ。

unquoted

  クォートされる文字列を含む文字列へのポインタ。

unquoted_len

  クォートされる文字列の長さ。

quoted

  クォートされた文字列へのポインタが返されるアドレスへのポインタ。

quoted_len

  新しい文字列の長さ。

param_type

  別のクォート形式を使用しているドライバ用の、ドライバ固有のヒント

この関数は、 PDO::quote() がコールされた場合、 あるいはドライバが supports_placeholder を `PDO_PLACEHOLDER_NONE` に設定した場合に PDO から呼び出されます。この関数の目的は、SQL ステートメントを 作成する際にパラメータをクォートすることです。

ドライバがネイティブのプリペアドステートメントをサポートしていない場合、 この関数を実装する必要があります。

この関数は、クォート処理が正しく行われた場合や文字列を変更する必要が なかった場合に 1、文字列の変更に失敗した場合に 0 を返します。 0 が返された場合、もとの文字列がそのまま使用されます。

#### SKEL_handle_begin

    static int SKEL_handle_begin(pdo_dbh_t *dbh TSRMLS_DC)

この関数は、データベースのトランザクションを開始する際に PDO から呼び出されます。

dbh

  ハンドルファクトリで初期化したデータベースハンドルへのポインタ。

トランザクションを開始するために必要な処理は、すべてここで 済ませる必要があります。この関数は、成功した場合に 1、 エラーが発生した場合に 0 を返します。

#### SKEL_handle_commit

    static int SKEL_handle_commit(pdo_dbh_t *dbh TSRMLS_DC)

この関数は、データベースのトランザクションを終了する際に PDO から呼び出されます。

dbh

  ハンドルファクトリで初期化したデータベースハンドルへのポインタ。

トランザクションをコミットするために必要な処理は、すべてここで 済ませる必要があります。この関数は、成功した場合に 1、 エラーが発生した場合に 0 を返します。

#### SKEL_handle_rollback

    static int SKEL_handle_rollback( pdo_dbh_t *dbh TSRMLS_DC)

この関数は、データベースのトランザクションをロールバックする際に PDO から呼び出されます。

dbh

  ハンドルファクトリで初期化したデータベースハンドルへのポインタ。

トランザクションをロールバックするために必要な処理は、すべてここで 済ませる必要があります。この関数は、成功した場合に 1、 エラーが発生した場合に 0 を返します。

#### SKEL_handle_get_attribute

    static int SKEL_handle_get_attribute(pdo_dbh_t *dbh, long attr, zval *return_value TSRMLS_DC)

この関数は、データベースの属性を取得するために PDO から呼び出されます。

dbh

  ハンドルファクトリで初期化したデータベースハンドルへのポインタ。

attr

  long 値。PDO_ATTR_xxxx 型のいずれか。使用可能な 値については 定数 を参照ください。

return_value

  返される属性の値。

実装においてどの属性をサポートするかは、ドライバ次第です。ドライバは 必ずこの関数を提供しなければならないわけではありません。 PDO_ATTR_PERSISTENT、PDO_ATTR_CASE、 PDO_ATTR_ORACLE_NULLS および PDO_ATTR_ERRMODE については PDO ドライバが 直接処理します。

この関数は、成功した場合に 1、失敗した場合に 0 を返します。

#### SKEL_handle_set_attribute

    static int SKEL_handle_set_attribute(pdo_dbh_t *dbh, long attr, zval *val TSRMLS_DC)

この関数は、データベースの属性を設定するために PDO から呼び出されます。 通常、これはスクリプトから PDO::setAttribute() をコールした場合に発生します。

dbh

  ハンドルファクトリで初期化したデータベースハンドルへのポインタ。

attr

  long 値。PDO_ATTR_xxxx 型のいずれか。使用可能な 値については 定数 を参照ください。

val

  属性の新しい値。

実装においてどの属性をサポートするかは、ドライバ次第です。 追加の属性をサポートする必要がないのであれば、ドライバは 必ずしもこの関数を提供しなくてもかまいません。 PDO_ATTR_CASE、 PDO_ATTR_ORACLE_NULLS および PDO_ATTR_ERRMODE については PDO ドライバが 直接処理します。

この関数は、成功した場合に 1、失敗した場合に 0 を返します。

#### SKEL_handle_last_id

    static char * SKEL_handle_last_id(pdo_dbh_t *dbh, const char *name, unsigned int len TSRMLS_DC)

この関数は、最後に挿入した行の ID を取得するために PDO から 呼び出されます。

dbh

  ハンドルファクトリで初期化したデータベースハンドルへのポインタ。

name

  テーブル名あるいはシーケンス名を表す文字列。

len

  パラメータ `name` の長さ。

この関数は、成功した場合には最後に挿入された行の ID を含む文字列、 失敗した場合には NULL を返します。これは、オプションの関数です。

#### SKEL_check_liveness

    static int SKEL_check_liveness(pdo_dbh_t *dbh TSRMLS_DC)

この関数は、データベースとの持続的接続が現在確立されているかどうかを 調べるために PDO から呼び出されます。

dbh

  ハンドルファクトリで初期化したデータベースハンドルへのポインタ。

この関数は、データベース接続が確立されており使用可能な状態の場合に 1、 それ以外の場合 (接続に失敗した場合や機能をサポートしていない場合など) に 0 を返します。

> 注意: これは、オプションの関数です。

#### SKEL_get_driver_methods

    static function_entry *SKEL_get_driver_methods(pdo_dbh_t *dbh, int kind TSRMLS_DC)

この関数は、PDO あるいは PDOStatement クラスに属さないメソッドが コールされた際に PDO から呼び出されます。この関数の目的は、 ドライバ固有のメソッドをクラスに追加できるようにすることです。

dbh

  ハンドルファクトリで初期化したデータベースハンドルへのポインタ。

kind

  以下のいずれか。

  PDO_DBH_DRIVER_METHOD_KIND_DBH

    PDO クラスのインスタンスに対して メソッドのコールが試みられた場合に設定します。 ドライバは、クラスに追加したいメソッドのための function_entry テーブルへのポインタか、それが存在しない場合には NULL を返す必要があります。

  PDO_DBH_DRIVER_METHOD_KIND_STMT

    PDOStatement クラスのインスタンスに対して メソッドのコールが試みられた場合に設定します。 ドライバは、クラスに追加したいメソッドのための function_entry テーブルへのポインタか、それが存在しない場合には NULL を返す必要があります。

この関数は、要求された function_entry テーブルへのポインタか、 ドライバ固有のメソッドが存在しない場合に NULL を返します。

#### SKEL_handle_factory

    static int SKEL_handle_factory(pdo_dbh_t *dbh, zval *driver_options TSRMLS_DC)

この関数は、データベースハンドルを作成するために PDO から呼び出されます。 ほとんどのデータベースでは、データベースへの接続がここに含まれます。 中には、持続的な接続が求められる場合もあります。あるいは接続ぷーリングが 求められる場合もあります。これらのすべては、データベース/ドライバ に依存します。

dbh

  ハンドルファクトリで初期化したデータベースハンドルへのポインタ。

driver_options

  ドライバのオプションの配列。整数値のオプション番号をキーとします。 指定できる属性の一覧は、 定数 を参照ください。

この関数は、成功した場合には、渡されたデータベースハンドル構造体に ドライバ固有の情報を格納して 1 を返し、それ以外の場合には 0 を返して 失敗したことを示します。

PDO は、handle_factory をコールする前に ドライバオプション AUTOCOMMIT および PERSISTENT を処理します。 その他のオプションを処理するのは、ハンドルファクトリの役目となります。

#### ドライバメソッドテーブル

pdo_dbh_methods 型のスタティックな構造体を SKEL_methods という名前で 宣言し、定義された関数へのポインタでそれを初期化しておく必要があります。 関数がサポートされていなかったり実装されていなかったりする場合は、 この関数ポインタの値を NULL に設定します。

#### pdo_SKEL_driver

pdo_driver_t 型の構造体を pdo_SKEL_driver という名前で宣言しなければ なりません。マクロ PDO_DRIVER_HEADER(SKEL) を使用して構造体の ヘッダを定義し、またハンドルファクトリ関数へのポインタを 設定しなければなりません。

### SKEL_statement.c: ステートメントの実装

ここでは、PDO ステートメントオブジェクトがサポートする すべてのステートメント処理メソッドを実装します。

#### SKEL_stmt_dtor

    static int SKEL_stmt_dtor(pdo_stmt_t *stmt TSRMLS_DC)

この関数は、事前に作成されたステートメントオブジェクトを 削除するために PDO から呼び出されます。

stmt

  SKEL_handle_preparer で初期化されたステートメント構造体へのポインタ。

ステートメントのために確保したドライバ固有の領域は、すべてここで 開放する必要があります。PDO は、この関数の返す値を無視します。

#### SKEL_stmt_execute

    static int SKEL_stmt_execute(pdo_stmt_t *stmt TSRMLS_DC)

この関数は、渡されたステートメントオブジェクト内のプリペアド SQL ステートメントを実行するために PDO から呼び出されます。

stmt

  SKEL_handle_preparer で初期化されたステートメント構造体へのポインタ。

この関数は、成功した場合に 1、失敗した場合に 0 を返します。

#### SKEL_stmt_fetch

    static int SKEL_stmt_fetch(pdo_stmt_t *stmt, enum pdo_fetch_orientation ori,
       long offset TSRMLS_DC)

この関数は、実行されたステートメントオブジェクトから行を取得するために PDO から呼び出されます。

stmt

  SKEL_handle_preparer で初期化されたステートメント構造体へのポインタ。

ori

  どの行を取得するのかを、PDO_FETCH_ORI_xxx のいずれかで指定します。

offset

  ori が PDO_FETCH_ORI_ABS あるいは PDO_FETCH_ORI_REL の場合、 offset はそれぞれ取得したい行の位置 あるいは現在の位置からの相対位置を表します。それ以外の場合は この値は無視されます。

この取得結果はドライバに依存し、データは通常 pdo_stmt_t オブジェクトの メンバ driver_data に格納されます。パラメータ ori および offset は、ステートメントがスクロール可能なカーソルを指している場合にのみ 意味を持ちます。この関数は、成功した場合に 1、失敗した場合に 0 を返します。

#### SKEL_stmt_param_hook

    static int SKEL_stmt_param_hook(pdo_stmt_t *stmt,
      struct pdo_bound_param_data *param, enum pdo_param_event event_type TSRMLS_DC)

この関数は、バインドされたパラメータやカラムを処理するために PDO から呼び出されます。

stmt

  SKEL_handle_preparer で初期化されたステートメント構造体へのポインタ。

param

  ステートメントのパラメータあるいはバインドされたカラムを表す構造体。

event_type

  このパラメータに発生するイベントの型。以下のいずれかです。

  PDO_PARAM_EVT_ALLOC

    PDO がバインドを割り当てる際にコールされます。 PDOStatement::bindParam() や PDOStatement::bindValue() のコール、あるいは PDOStatement::execute() による暗黙的な バインドの際に発生します。この時点で、何らかのアクションを とることができます。プリペアドステートメントをネイティブに 実装するドライバの場合、典型的なアクションとしては パラメータの情報の取得・スクリプトで要求された型との調整・ 適切な大きさのバッファの確保・そしてバッファへのパラメータの バインドなどがあるでしょう。 この時点では、param->parameter の zval の 型や値をあてにすべきではありません。

  PDO_PARAM_EVT_FREE

    各パラメータが開放される際にコールされます。パラメータに 関連するすべてのリソースはここで開放しなければなりません。

  PDO_PARAM_EXEC_PRE

    SKEL_stmt_execute がコールされる直前に、パラメータごとにコールされます。 実行前の最後の調整をここで行います。特に注意すべき点として、 PDOStatement::bindParam() による変数のバインドは ここでのみ行うべきで、それより前の段階で行ってはなりません。

  PDO_PARAM_EXEC_POST

    SKEL_stmt_execute がコールされた直後に、パラメータごとにコールされます。 ドライバが必要とする後処理をここで行います。

  PDO_PARAM_FETCH_PRE

    SKEL_stmt_fetch がコールされる直前に、パラメータごとにコールされます。

  PDO_PARAM_FETCH_POST

    SKEL_stmt_fetch がコールされた直後に、パラメータごとにコールされます。

このフックは、ステートメント内でバインドされたパラメータおよびカラムの それぞれについて、個々にコールされます。ALLOC および FREE イベントは、 各パラメータあるいはカラムについて 1 度コールされます。 param 構造体は driver_data フィールドを含み、これは 各パラメータについての実装固有の情報を格納するために使用されます。

その他のすべてのイベントでは、スクリプトが PDOStatement::execute() および PDOStatement::fetch() をコールするたびに PDO からコールされることになります。

バインドされたのが変数の場合、param 構造体の is_param フラグが 設定されています。それ以外の場合は param 構造体はバインドカラムを 表します。

この関数は、成功した場合に 1、失敗した場合に 0 を返します。

#### SKEL_stmt_describe_col

    static int SKEL_stmt_describe_col(pdo_stmt_t *stmt, int colno TSRMLS_DC)

この関数は、特定のカラムについての情報を問い合わせるために PDO からコールされます。

stmt

  SKEL_handle_preparer で初期化されたステートメント構造体へのポインタ。

colno

  調べたいカラムの番号。

ドライバは、pdo_stmt_t のメンバ columns(colno) に適切な情報を格納する 必要があります。この関数は、成功した場合に 1、失敗した場合に 0 を返します。

#### SKEL_stmt_get_col_data

    static int SKEL_stmt_get_col_data(pdo_stmt_t *stmt, int colno,
      char **ptr, unsigned long *len, int *caller_frees TSRMLS_DC)

この関数は、指定したカラムからデータを取得するために PDO から呼び出されます。

stmt

  SKEL_handle_preparer で初期化されたステートメント構造体へのポインタ。

colno

  取得したいカラムの番号。

ptr

  取得したデータへのポインタ。

len

  ptf が指すデータの長さ。

caller_frees

  設定されている場合は ptf が指すメモリは emalloc されたものであり、 使用終了後にメイン PDO ドライバがそれを開放する必要があります。 設定されていない場合は、このコールの結果として確保されたメモリを 開放するのはドライバの役目となります。

ドライバは、結果のデータおよびその長さをそれぞれ ptr および len に 返す必要があります。メイン PDO ドライバは、データの生存期間を ドライバが管理するものと想定していることに注意しましょう。 この関数は、成功した場合に 1、失敗した場合に 0 を返します。

#### SKEL_stmt_set_attr

    static int SKEL_stmt_set_attr(pdo_stmt_t *stmt, long attr, zval *val TSRMLS_DC)

この関数は、ステートメントオブジェクトのドライバ固有の属性を 設定するために PDO から呼び出されます。

stmt

  SKEL_handle_preparer で初期化されたステートメント構造体へのポインタ。

attr

  long 値。PDO_ATTR_xxxx 型のいずれか。使用可能な 値については 定数 を参照ください。

val

  属性の新しい値。

この関数はドライバに依存しており、ステートメントにデータベース固有の 属性を設定する機能を与えます。この関数は、成功した場合に 1、 失敗した場合に 0 を返します。これはオプションの関数です。 もし設定可能な追加属性をドライバがサポートしていない場合は、 メソッドテーブルで NULL を設定しておくことも可能です。PDO ドライバは、 データベースドライバに代わって設定可能属性の処理を行うことはありません。

#### SKEL_stmt_get_attr

    static int SKEL_stmt_get_attr(pdo_stmt_t *stmt, long attr, zval
       *return_value TSRMLS_DC)

この関数は、ステートメントオブジェクトのドライバ固有の属性を 取得するために PDO から呼び出されます。

stmt

  SKEL_handle_preparer で初期化されたステートメント構造体へのポインタ。

attr

  long 値。PDO_ATTR_xxxx 型のいずれか。使用可能な 値については 定数 を参照ください。

return_value

  返される属性の値。

この関数はドライバに依存しており、ステートメントからデータベース固有の 属性を取得する機能を与えます。この関数は、成功した場合に 1、 失敗した場合に 0 を返します。これはオプションの関数です。 もし取得可能な追加属性をドライバがサポートしていない場合は、 メソッドテーブルで NULL を設定しておくことも可能です。PDO ドライバは、 データベースドライバに代わって取得可能属性の処理を行うことはありません。

#### SKEL_stmt_get_col_meta

    static int SKEL_stmt_get_col_meta(pdo_stmt_t *stmt, int colno,
       zval *return_value TSRMLS_DC)

警告

この関数はうまく定義されておれず、変更する必要があります。

この関数は、指定したカラムのメタデータを取得するために PDO から呼び出されます。

stmt

  SKEL_handle_preparer で初期化されたステートメント構造体へのポインタ。

colno

  データを取得するカラム番号。

return_value

  返されるメタデータを保持します。

ドライバの作者は、php_pdo_driver.h ヘッダに書かれているこの関数の ドキュメントを参照し、最新の情報を得てください。 この関数は、成功した場合に 1、失敗した場合に 0 を返します。 データベースドライバは、この関数を提供する必要はありません。

#### ステートメント操作メソッドテーブル

pdo_stmt_methods 型のスタティックな構造体を SKEL_stmt_methods という名前で 宣言し、定義された関数へのポインタでそれを初期化しておく必要があります。 関数がサポートされていなかったり実装されていなかったりする場合は、 この関数ポインタの値を NULL に設定します。

準備
ビルド
PDO ドライバ How-To
PHP Manual