Commit 05147fbe authored by romanb's avatar romanb

Completed implementation of the query cache.

parent bbfa506d
...@@ -182,11 +182,15 @@ final class Doctrine ...@@ -182,11 +182,15 @@ final class Doctrine
const ATTR_COLL_LIMIT = 123; const ATTR_COLL_LIMIT = 123;
const ATTR_CACHE = 150; const ATTR_CACHE = 150;
const ATTR_RESULT_CACHE = 150;
const ATTR_CACHE_LIFESPAN = 151; const ATTR_CACHE_LIFESPAN = 151;
const ATTR_RESULT_CACHE_LIFESPAN = 151;
const ATTR_LOAD_REFERENCES = 153; const ATTR_LOAD_REFERENCES = 153;
const ATTR_RECORD_LISTENER = 154; const ATTR_RECORD_LISTENER = 154;
const ATTR_THROW_EXCEPTIONS = 155; const ATTR_THROW_EXCEPTIONS = 155;
const ATTR_DEFAULT_PARAM_NAMESPACE = 156; const ATTR_DEFAULT_PARAM_NAMESPACE = 156;
const ATTR_QUERY_CACHE = 157;
const ATTR_QUERY_CACHE_LIFESPAN = 158;
/** /**
* LIMIT CONSTANTS * LIMIT CONSTANTS
......
...@@ -102,6 +102,8 @@ abstract class Doctrine_Configurable extends Doctrine_Locator_Injectable ...@@ -102,6 +102,8 @@ abstract class Doctrine_Configurable extends Doctrine_Locator_Injectable
} }
break; break;
case Doctrine::ATTR_CACHE: case Doctrine::ATTR_CACHE:
case Doctrine::ATTR_RESULT_CACHE:
case Doctrine::ATTR_QUERY_CACHE:
if ($value !== null) { if ($value !== null) {
if ( ! ($value instanceof Doctrine_Cache_Interface)) { if ( ! ($value instanceof Doctrine_Cache_Interface)) {
throw new Doctrine_Exception('Cache driver should implement Doctrine_Cache_Interface'); throw new Doctrine_Exception('Cache driver should implement Doctrine_Cache_Interface');
......
...@@ -1218,11 +1218,25 @@ abstract class Doctrine_Connection extends Doctrine_Configurable implements Coun ...@@ -1218,11 +1218,25 @@ abstract class Doctrine_Connection extends Doctrine_Configurable implements Coun
*/ */
public function getResultCacheDriver() public function getResultCacheDriver()
{ {
if ( ! isset($this->attributes[Doctrine::ATTR_CACHE])) { if ( ! $this->getAttribute(Doctrine::ATTR_RESULT_CACHE)) {
throw new Doctrine_Exception('Result Cache driver not initialized.'); throw new Doctrine_Exception('Result Cache driver not initialized.');
} }
return $this->attributes[Doctrine::ATTR_CACHE]; return $this->getAttribute(Doctrine::ATTR_RESULT_CACHE);
}
/**
* getQueryCacheDriver
*
* @return Doctrine_Cache_Interface
*/
public function getQueryCacheDriver()
{
if ( ! $this->getAttribute(Doctrine::ATTR_QUERY_CACHE)) {
throw new Doctrine_Exception('Query Cache driver not initialized.');
}
return $this->getAttribute(Doctrine::ATTR_QUERY_CACHE);
} }
/** /**
......
...@@ -53,7 +53,7 @@ class Doctrine_Hydrator extends Doctrine_Hydrator_Abstract ...@@ -53,7 +53,7 @@ class Doctrine_Hydrator extends Doctrine_Hydrator_Abstract
* 'table' => Table object, * 'table' => Table object,
* 'parent' => Parent DQL alias (if any), * 'parent' => Parent DQL alias (if any),
* 'relation' => Relation object (if any), * 'relation' => Relation object (if any),
* 'map' => ??? (if any) * 'map' => Custom index to use as the key in the result (if any)
* ) * )
* ) * )
* @return array * @return array
......
...@@ -92,6 +92,8 @@ class Doctrine_Manager extends Doctrine_Configurable implements Countable, Itera ...@@ -92,6 +92,8 @@ class Doctrine_Manager extends Doctrine_Configurable implements Countable, Itera
$init = true; $init = true;
$attributes = array( $attributes = array(
Doctrine::ATTR_CACHE => null, Doctrine::ATTR_CACHE => null,
Doctrine::ATTR_RESULT_CACHE => null,
Doctrine::ATTR_QUERY_CACHE => null,
Doctrine::ATTR_LOAD_REFERENCES => true, Doctrine::ATTR_LOAD_REFERENCES => true,
Doctrine::ATTR_LISTENER => new Doctrine_EventListener(), Doctrine::ATTR_LISTENER => new Doctrine_EventListener(),
Doctrine::ATTR_RECORD_LISTENER => new Doctrine_Record_Listener(), Doctrine::ATTR_RECORD_LISTENER => new Doctrine_Record_Listener(),
......
...@@ -869,11 +869,11 @@ abstract class Doctrine_Query_Abstract ...@@ -869,11 +869,11 @@ abstract class Doctrine_Query_Abstract
$params = $this->_conn->convertBooleans($params); $params = $this->_conn->convertBooleans($params);
if ( ! $this->_view) { if ( ! $this->_view) {
if ($this->_queryCache) { if ($this->_queryCache || $this->_conn->getAttribute(Doctrine::ATTR_QUERY_CACHE)) {
$queryCacheDriver = $this->getQueryCacheDriver(); $queryCacheDriver = $this->getQueryCacheDriver();
// calculate hash for dql query // calculate hash for dql query
$dql = $this->getDql(); $dql = $this->getDql();
$hash = md5($dql); $hash = md5($dql . 'DOCTRINE_QUERY_CACHE_SALT');
$cached = $queryCacheDriver->fetch($hash); $cached = $queryCacheDriver->fetch($hash);
if ($cached) { if ($cached) {
$query = $this->_constructQueryFromCache($cached); $query = $this->_constructQueryFromCache($cached);
...@@ -1520,14 +1520,9 @@ abstract class Doctrine_Query_Abstract ...@@ -1520,14 +1520,9 @@ abstract class Doctrine_Query_Abstract
* @param integer $timeToLive how long the cache entry is valid * @param integer $timeToLive how long the cache entry is valid
* @return Doctrine_Hydrate this object * @return Doctrine_Hydrate this object
*/ */
public function useQueryCache($driver = true, $timeToLive = null) public function useQueryCache(Doctrine_Cache_Interface $driver, $timeToLive = null)
{ {
if ($driver !== null && $driver !== true && ! ($driver instanceof Doctrine_Cache_Interface)){
$msg = 'First argument should be instance of Doctrine_Cache_Interface or null.';
throw new Doctrine_Query_Exception($msg);
}
$this->_queryCache = $driver; $this->_queryCache = $driver;
return $this->setQueryCacheLifeSpan($timeToLive); return $this->setQueryCacheLifeSpan($timeToLive);
} }
......
...@@ -37,11 +37,30 @@ class Doctrine_Query_Cache_TestCase extends Doctrine_UnitTestCase ...@@ -37,11 +37,30 @@ class Doctrine_Query_Cache_TestCase extends Doctrine_UnitTestCase
{ {
$cache = new Doctrine_Cache_Array(); $cache = new Doctrine_Cache_Array();
$q = new Doctrine_Query(); $q = new Doctrine_Query();
$q->select('u.name')->from('User u')->leftJoin('u.Phonenumber p') $q->select('u.name')->from('User u')->leftJoin('u.Phonenumber p')->where('u.name = ?', 'walhala')
->useQueryCache($cache); ->useQueryCache($cache);
$coll = $q->execute(); $coll = $q->execute();
$this->assertEqual($cache->count(), 1);
$this->assertEqual(count($coll), 0);
$coll = $q->execute();
$this->assertEqual($cache->count(), 1);
$this->assertEqual(count($coll), 0);
}
public function testQueryCacheWorksWithGlobalConfiguration()
{
$cache = new Doctrine_Cache_Array();
Doctrine_Manager::getInstance()->setAttribute(Doctrine::ATTR_QUERY_CACHE, $cache);
$q = new Doctrine_Query();
$q->select('u.name')->from('User u')->leftJoin('u.Phonenumber p');
$coll = $q->execute();
$this->assertEqual($cache->count(), 1); $this->assertEqual($cache->count(), 1);
$this->assertEqual(count($coll), 8); $this->assertEqual(count($coll), 8);
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment