こんにちはゲストさん。会員登録(無料)して質問・回答してみよう!

解決済みの質問

PHPからMySQLへのクエリの振り分け方法

LAMP構成のWebアプリケーションでのDBサーバ増設について質問です。

今までDBサーバ(MySQL)1台で運用していたのですが、
1台増設してレプリケーションを行うことになりました。

DBサーバ1:マスター(新設)
DBサーバ2:スレーブ

そこで、PHPスクリプトを全面的に見直して、以下のように
DBへのコネクション部分を変更する必要が出てきました。

・コネクション中に一度でも更新系のクエリを発行する場合はマスターへ
・それ以外はスレーブへ

これをインクルード先まで追って調査するのは現実的ではないため、
一括で振り分ける方法を探しています。

雑で申し訳ありませんが、環境は以下の通りです。
PHP 5.1.6 (cli)
PEAR::DB(1.7.13)
MySQL 4.1.22

投稿日時 - 2009-08-25 18:02:33

QNo.5235966

すぐに回答ほしいです

質問者が選んだベストアンサー

まったくの未検証ですが、
PEAR::DBのインスタンスを作成する場所で、代わりに、PEAR::DBのインスタンス(マスターとスレーブの二つ)に接続するハブクラスを作成したら最小限の改修でいくかもしれませんが、どうでしょう。
<?php

class DBR{

public static function connect($dsn){

return new DBR_mysql($dsn);

}
}

class DBR_mysql{

protected $DB = array();

public function __construct($dsn){
$this->DB['master'] = DB::connect($dsn['master']);
$this->DB['slave'] = DB::connect($dsn['slave']);
}

public function __call($method, $params){
if($method == 'query'){
if(preg_match('/^\s*SELECT/i', $params[0])){
return call_user_func_array(array($this->DB['slave']), $params);
}
}
return call_user_func_array(array($this->DB['master']), $params);
}

}
?>

このようにすれば、PEAR::DBのインスタンス作成箇所を
<?php
$obj = DB::connect("DSN情報");
?>
と記述してあるものを
<?php
$obj = DBR::connect(array('master'=>"マスタのDSN", 'slave'=>"スレーブのDSN"));
?>
と記述してやると、オーバーロードした__callメソッドにて、基本的に全てmasterに振って、queryメソッドで「SELECT」から始まるもののみ、スレーブに振り分ける、ということが出来ます。
PEAR::DBをちゃんと利用したことが無いので、queryメソッドだけを振り分ければそれでいけるのかは分かりませんが・・・

投稿日時 - 2009-08-26 00:20:06

お礼

hogehoge78さま

とても参考になりました。ほぼそのままの内容でいけそうです。
迅速なご回答を頂きましてありがとうございました!

投稿日時 - 2009-08-26 14:28:09

このQ&Aは役に立ちましたか?

0人が「このQ&Aが役に立った」と投票しています

回答(1)

あなたにオススメの質問