2010年10月26日

CakePHP1.2 CacheBehaviorでモデルのメソッドキャッシュ

http://www.exgear.jp/blog/2008/11/method_cache_behavior/
http://d.hatena.ne.jp/lifegood/20090604/p1
こちらを元ネタにして
若干改良をほどこしました。

1.CacheBehaviorの導入


class CacheBehavior extends ModelBehavior {
var $enabled = true;

var $config = array();

function setup(&$model, $config = array()) {
$this->config[$model->alias] = $config;
}

//config設定
function _setConfig(&$model,$config = null){
if(empty($config)){
$config = $this->config[$model->alias];
}
if(is_array($config)){
if(!empty($config['config'])){
$config = $config['config'];
}else{
$config = null;
}
}
return $config;
}

/**
* メソッドキャッシュ
*/
function cacheMethod(&$model, $method, $args = array(),$config = null){
$config = $this->_setConfig($model,$config);

$this->enabled = false;
// キャッシュキー
$cachekey = $this->createCacheKey($model, $method, $args ,$config);

$ret = Cache::read($cachekey,$config);
if(!empty($ret)){
$this->enabled = true;
return $ret;
}
$ret = call_user_func_array(array($model, $method), $args);
$this->enabled = true;
Cache::write($cachekey, $ret, $config);
// クリア用にモデル毎のキャッシュキーリストを作成
$cacheListKey = get_class($model) . '_cacheMethodList';
$list = Cache::read($cacheListKey);
$list[$cachekey] = $config;
Cache::write($cacheListKey, $list);
return $ret;
}

/**
* キャッシュキーの生成
*
*/
function createCacheKey(&$model, $method, $args = array(),$config = null){
return get_class($model) . '_' . $method . '_' . $this->_setConfig($model,$config) . '_' . md5(serialize($args));
}
/**
* 再帰防止判定用
*/
function cacheEnabled(&$model){
return $this->enabled;
}
/**
* キャッシュ個別クリア
*/
function cacheDelete(&$model, $method, $args = array(),$config = null){
$config = $this->_setConfig($model,$config);
$cacheListKey = $this->createCacheKey($model, $method, $args, $config);
Cache::delete($cacheListKey,$config);

}
/**
* キャッシュ全クリア
*/
function cacheDeleteAll(&$model){
$cacheListKey = get_class($model) . '_cacheMethodList';
$list = Cache::read($cacheListKey);
if(empty($list)) return;
foreach($list as $key => $config){
Cache::delete($key,$config);
}
Cache::delete($cacheListKey);
}
/**
* 追加・変更・削除時にはキャッシュをクリア
*/
function afterSave(&$model, $created) {
$this->cacheDeleteAll($model);
}
function afterDelete(&$model) {
$this->cacheDeleteAll($model);
}
}




2.find()のオーバーライド

class AppModel extends Model {
var $actsAs = array('Cache' => array('config'=>'_app_find_'));

function find($conditions = null, $fields = array(), $order = null, $recursive = null) {

// Call cache method
$args = func_get_args();
if ($this->Behaviors->attached('Cache')) {
if($this->cacheEnabled()) {
return $this->cacheMethod(__FUNCTION__, $args );
}
}
// Case normal find. The model does not have cache behavior.
return parent::find($conditions, $fields, $order, $recursive);
}
}


【cakePHPの最新記事】

この記事へのトラックバックURL

http://blogs.dion.ne.jp/muller/tb.cgi/9782048
※ブログオーナーが承認したトラックバックのみ表示されます。
※半角英数字のみのトラックバックは受信されません。
※言及リンクのないトラックバックは受信されません。
 
※ブログオーナーが承認したコメントのみ表示されます。
※半角英数字のみのコメントは投稿できません。