1
0
mirror of synced 2025-02-02 13:31:45 +03:00

Evict query cache when entities are updated

This commit is contained in:
Luís Cobucci 2016-09-02 09:54:14 +00:00 committed by Marco Pivetta
parent bf18aac62d
commit 88567ea395
4 changed files with 78 additions and 4 deletions

View File

@ -110,7 +110,9 @@ class CacheConfiguration
public function getQueryValidator()
{
if ($this->queryValidator === null) {
$this->queryValidator = new TimestampQueryCacheValidator();
$this->queryValidator = new TimestampQueryCacheValidator(
$this->cacheFactory->getTimestampRegion()
);
}
return $this->queryValidator;

View File

@ -26,15 +26,49 @@ namespace Doctrine\ORM\Cache;
*/
class TimestampQueryCacheValidator implements QueryCacheValidator
{
/**
* @var TimestampRegion
*/
private $timestampRegion;
/**
* @param TimestampRegion $timestampRegion
*/
public function __construct(TimestampRegion $timestampRegion)
{
$this->timestampRegion = $timestampRegion;
}
/**
* {@inheritdoc}
*/
public function isValid(QueryCacheKey $key, QueryCacheEntry $entry)
{
if ($this->regionUpdated($key, $entry)) {
return false;
}
if ($key->lifetime == 0) {
return true;
}
return ($entry->time + $key->lifetime) > microtime(true);
}
/**
* @param QueryCacheKey $key
* @param QueryCacheEntry $entry
*
* @return bool
*/
private function regionUpdated(QueryCacheKey $key, QueryCacheEntry $entry)
{
if ($key->timestampKey === null) {
return false;
}
$timestamp = $this->timestampRegion->get($key->timestampKey);
return $timestamp && $timestamp->time > $entry->time;
}
}

View File

@ -2,8 +2,8 @@
namespace Doctrine\Tests\ORM\Cache;
use Doctrine\Tests\DoctrineTestCase;
use Doctrine\ORM\Cache\CacheConfiguration;
use Doctrine\Tests\DoctrineTestCase;
/**
* @group DDC-2183
@ -64,6 +64,11 @@ class CacheConfigTest extends DoctrineTestCase
public function testSetGetQueryValidator()
{
$factory = $this->getMock('Doctrine\ORM\Cache\CacheFactory');
$factory->method('getTimestampRegion')->willReturn($this->getMock('Doctrine\ORM\Cache\TimestampRegion'));
$this->config->setCacheFactory($factory);
$validator = $this->getMock('Doctrine\ORM\Cache\QueryCacheValidator');
$this->assertInstanceOf('Doctrine\ORM\Cache\TimestampQueryCacheValidator', $this->config->getQueryValidator());
@ -72,4 +77,4 @@ class CacheConfigTest extends DoctrineTestCase
$this->assertEquals($validator, $this->config->getQueryValidator());
}
}
}

View File

@ -1035,4 +1035,37 @@ class SecondLevelCacheQueryCacheTest extends SecondLevelCacheAbstractTest
->setCacheable(true)
->getResult();
}
}
public function testQueryCacheShouldBeEvictedOnTimestampUpdate()
{
$this->loadFixturesCountries();
$this->_em->clear();
$queryCount = $this->getCurrentQueryCount();
$dql = 'SELECT country FROM Doctrine\Tests\Models\Cache\Country country';
$result1 = $this->_em->createQuery($dql)
->setCacheable(true)
->getResult();
$this->assertCount(2, $result1);
$this->assertEquals($queryCount + 1, $this->getCurrentQueryCount());
$this->_em->persist(new Country('France'));
$this->_em->flush();
$this->_em->clear();
$queryCount = $this->getCurrentQueryCount();
$result2 = $this->_em->createQuery($dql)
->setCacheable(true)
->getResult();
$this->assertCount(3, $result2);
$this->assertEquals($queryCount + 1, $this->getCurrentQueryCount());
foreach ($result2 as $entity) {
$this->assertInstanceOf(Country::CLASSNAME, $entity);
}
}
}