Skip to content

Commit

Permalink
[PropertyAccess] Add Doctrine Cache
Browse files Browse the repository at this point in the history
  • Loading branch information
dunglas committed Dec 4, 2015
1 parent 582f475 commit c0e70a7
Show file tree
Hide file tree
Showing 5 changed files with 81 additions and 4 deletions.
24 changes: 21 additions & 3 deletions src/Symfony/Component/PropertyAccess/PropertyAccessor.php
Expand Up @@ -11,6 +11,7 @@

namespace Symfony\Component\PropertyAccess;

use Doctrine\Common\Cache\Cache;
use Symfony\Component\PropertyAccess\Exception\AccessException;
use Symfony\Component\PropertyAccess\Exception\NoSuchPropertyException;
use Symfony\Component\PropertyAccess\Exception\NoSuchIndexException;
Expand Down Expand Up @@ -38,6 +39,9 @@ class PropertyAccessor implements PropertyAccessorInterface
const ACCESS_TYPE_MAGIC = 2;
const ACCESS_TYPE_ADDER_AND_REMOVER = 3;
const ACCESS_TYPE_NOT_FOUND = 4;
const CACHE_PREFIX_PROPERTY_PATH = 'pp';
const CACHE_PREFIX_READ = 'r';
const CACHE_PREFIX_WRITE = 'w';

/**
* @var bool
Expand All @@ -49,6 +53,11 @@ class PropertyAccessor implements PropertyAccessorInterface
*/
private $ignoreInvalidIndices;

/**
* @var Cache
*/
private $cache;

/**
* @var array
*/
Expand All @@ -63,10 +72,11 @@ class PropertyAccessor implements PropertyAccessorInterface
* Should not be used by application code. Use
* {@link PropertyAccess::createPropertyAccessor()} instead.
*/
public function __construct($magicCall = false, $throwExceptionOnInvalidIndex = false)
public function __construct($magicCall = false, $throwExceptionOnInvalidIndex = false, Cache $cache = null)
{
$this->magicCall = $magicCall;
$this->ignoreInvalidIndices = !$throwExceptionOnInvalidIndex;
$this->cache = $cache;
}

/**
Expand Down Expand Up @@ -401,7 +411,7 @@ private function getReadAccessInfo($object, $property)

if (isset($this->readPropertyCache[$key])) {
$access = $this->readPropertyCache[$key];
} else {
} elseif (!$this->cache || !$access = $this->cache->fetch(self::CACHE_PREFIX_READ.$key)) {
$access = array();

$reflClass = new \ReflectionClass($object);
Expand Down Expand Up @@ -456,6 +466,10 @@ private function getReadAccessInfo($object, $property)
);
}

if ($this->cache) {
$this->cache->save(self::CACHE_PREFIX_READ.$key, $access);
}

$this->readPropertyCache[$key] = $access;
}

Expand Down Expand Up @@ -583,7 +597,7 @@ private function getWriteAccessInfo($object, $property, $value)

if (isset($this->writePropertyCache[$key])) {
$access = $this->writePropertyCache[$key];
} else {
} elseif (!$this->cache || !$access = $this->cache->fetch(self::CACHE_PREFIX_WRITE.$key)) {
$access = array();

$reflClass = new \ReflectionClass($object);
Expand Down Expand Up @@ -645,6 +659,10 @@ private function getWriteAccessInfo($object, $property, $value)
}
}

if ($this->cache) {
$this->cache->save(self::CACHE_PREFIX_WRITE.$key, $access);
}

$this->writePropertyCache[$key] = $access;
}

Expand Down
33 changes: 32 additions & 1 deletion src/Symfony/Component/PropertyAccess/PropertyAccessorBuilder.php
Expand Up @@ -11,6 +11,8 @@

namespace Symfony\Component\PropertyAccess;

use Doctrine\Common\Cache\Cache;

/**
* A configurable builder to create a PropertyAccessor.
*
Expand All @@ -28,6 +30,11 @@ class PropertyAccessorBuilder
*/
private $throwExceptionOnInvalidIndex = false;

/**
* @var Cache|null
*/
private $cache;

/**
* Enables the use of "__call" by the PropertyAccessor.
*
Expand Down Expand Up @@ -97,13 +104,37 @@ public function isExceptionOnInvalidIndexEnabled()
return $this->throwExceptionOnInvalidIndex;
}

/**
* Uses a cache system.
*
* @param Cache|null $cache
*
* @return PropertyAccessorBuilder The builder object
*/
public function useCache(Cache $cache = null)
{
$this->cache = $cache;

return $this;
}

/**
* Gets the cache system.
*
* @return Cache|null
*/
public function getCache()
{
return $this->cache;
}

/**
* Builds and returns a new PropertyAccessor object.
*
* @return PropertyAccessorInterface The built PropertyAccessor
*/
public function getPropertyAccessor()
{
return new PropertyAccessor($this->magicCall, $this->throwExceptionOnInvalidIndex);
return new PropertyAccessor($this->magicCall, $this->throwExceptionOnInvalidIndex, $this->cache);
}
}
Expand Up @@ -11,6 +11,7 @@

namespace Symfony\Component\PropertyAccess\Tests;

use Doctrine\Common\Cache\ArrayCache;
use Symfony\Component\PropertyAccess\PropertyAccessorBuilder;

class PropertyAccessorBuilderTest extends \PHPUnit_Framework_TestCase
Expand Down Expand Up @@ -52,4 +53,12 @@ public function testGetPropertyAccessor()
$this->assertInstanceOf('Symfony\Component\PropertyAccess\PropertyAccessor', $this->builder->getPropertyAccessor());
$this->assertInstanceOf('Symfony\Component\PropertyAccess\PropertyAccessor', $this->builder->enableMagicCall()->getPropertyAccessor());
}

public function testUseCache()
{
$cache = new ArrayCache();
$this->builder->useCache($cache);
$this->assertEquals($cache, $this->builder->getCache());
$this->assertInstanceOf('Symfony\Component\PropertyAccess\PropertyAccessor', $this->builder->getPropertyAccessor());
}
}
Expand Up @@ -11,6 +11,8 @@

namespace Symfony\Component\PropertyAccess\Tests;

use Doctrine\Common\Cache\ArrayCache;
use Doctrine\Common\Cache\Cache;
use Symfony\Component\PropertyAccess\Exception\NoSuchIndexException;
use Symfony\Component\PropertyAccess\PropertyAccessor;
use Symfony\Component\PropertyAccess\Tests\Fixtures\TestClass;
Expand Down Expand Up @@ -510,4 +512,15 @@ public function testIsWritableForReferenceChainIssue($object, $path, $value)
{
$this->assertEquals($value, $this->propertyAccessor->isWritable($object, $path));
}

public function testCacheReadAccess()
{
$obj = new TestClass('foo');

$propertyAccessor = new PropertyAccessor(false, false, new ArrayCache());
$this->assertEquals('foo', $propertyAccessor->getValue($obj, 'publicAccessor'));
$propertyAccessor->setValue($obj, 'publicAccessor', 'bar');
$propertyAccessor->setValue($obj, 'publicAccessor', 'baz');
$this->assertEquals('baz', $propertyAccessor->getValue($obj, 'publicAccessor'));
}
}
6 changes: 6 additions & 0 deletions src/Symfony/Component/PropertyAccess/composer.json
Expand Up @@ -18,6 +18,12 @@
"require": {
"php": ">=5.5.9"
},
"require-dev": {
"doctrine/cache": "~1.0"
},
"suggest": {
"doctrine/cache": "To cache access methods"
},
"autoload": {
"psr-4": { "Symfony\\Component\\PropertyAccess\\": "" },
"exclude-from-classmap": [
Expand Down

0 comments on commit c0e70a7

Please sign in to comment.