PEARのCacheを利用してPostgreSQLのクエリを高速化するには?
【Tips】PEARのCacheクラスを継承!
【Description】データベースの件数やSQLの複雑さに依存するので一概に言えないが、1万件のレコードをそのまま引っ張ってくるような場合で3倍程度高速です(シャア専用ってことです)。
Expireを上手に変えれば結構使える箇所は多いはず。日次でマスターが変更されるような場合3600秒のままでも問題なし。クエリの結果が巨大な場合はphpのメモリ上限を変更しないとダメなことも。以下のように使います。
$cache = new PGSQL_Query_Cache();
$cache->connect("DB_NAME", "DB_USER");
if($res = $cache->query("SELECT * FROM TABLE")){
while($row = $cache->fetch_row()){
echo($row[FLD_NAME]);
}
}
<?php
require_once "Cache.php";
class PGSQL_Query_Cache extends Cache {
var $connection = null;
var $expires = 3600;
var $cursor = 0;
var $result = array();
function PGSQL_Query_Cache($container = "file", $container_options = array("cache_dir"=> "/tmp/", "filename_prefix" => "cache_"), $expires = 3600){
$this->Cache($container, $container_options);
$this->expires = $expires;
}
function _PGSQL_Query_Cache() {
if(is_resource($this->connection)){
pg_close($this->connection);
}
$this->_Cache();
}
function connect($database, $username){
$this->connection = pg_pconnect("dbname=".$database." user=".$username) or trigger_error('Could not connect to database.', E_USER_ERROR);
}
function fetch_row(){
if($this->cursor < sizeof($this->result)){
return $this->result[$this->cursor++];
} else {
return false;
}
}
function num_rows(){
return sizeof($this->result);
}
function query($query){
if(stristr($query, 'SELECT')){
$cache_id = md5($query);
$this->result = $this->get($cache_id, 'pgsql_query_cache');
if(!$this->result){
$this->cursor = 0;
$this->result = array();
if(is_resource($this->connection)){
$result = pg_query($this->connection, $query);
while($row = pg_fetch_assoc($result)){
$this->result[] = $row;
}
pg_free_result($result);
$this->save($cache_id, $this->result, $this->expires, 'pgsql_query_cache');
}
}
return $this->result;
} else {
return pg_query($this->connection, $query);
}
}
}
?>