Movatterモバイル変換


[0]ホーム

URL:


Skip to content

Navigation Menu

Sign in
Appearance settings

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Sign up
Appearance settings

Commitf336e86

Browse files
committed
[FrameworkBundle] Introduce a cache warmer for Serializer based on PhpArrayAdapter
1 parent983b560 commitf336e86

File tree

12 files changed

+330
-35
lines changed

12 files changed

+330
-35
lines changed
Lines changed: 106 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,106 @@
1+
<?php
2+
3+
/*
4+
* This file is part of the Symfony package.
5+
*
6+
* (c) Fabien Potencier <fabien@symfony.com>
7+
*
8+
* For the full copyright and license information, please view the LICENSE
9+
* file that was distributed with this source code.
10+
*/
11+
12+
namespaceSymfony\Bundle\FrameworkBundle\CacheWarmer;
13+
14+
usePsr\Cache\CacheItemPoolInterface;
15+
useSymfony\Component\Cache\Adapter\AdapterInterface;
16+
useSymfony\Component\Cache\Adapter\ArrayAdapter;
17+
useSymfony\Component\Cache\Adapter\PhpArrayAdapter;
18+
useSymfony\Component\Cache\Adapter\ProxyAdapter;
19+
useSymfony\Component\HttpKernel\CacheWarmer\CacheWarmerInterface;
20+
useSymfony\Component\Serializer\Mapping\Factory\CacheClassMetadataFactory;
21+
useSymfony\Component\Serializer\Mapping\Factory\ClassMetadataFactory;
22+
useSymfony\Component\Serializer\Mapping\Loader\LoaderChain;
23+
useSymfony\Component\Serializer\Mapping\Loader\LoaderInterface;
24+
useSymfony\Component\Serializer\Mapping\Loader\XmlFileLoader;
25+
useSymfony\Component\Serializer\Mapping\Loader\YamlFileLoader;
26+
27+
/**
28+
* Warms up XML and YAML serializer metadata.
29+
*
30+
* @author Titouan Galopin <galopintitouan@gmail.com>
31+
*/
32+
class SerializerCacheWarmerimplements CacheWarmerInterface
33+
{
34+
private$loader;
35+
private$phpArrayFile;
36+
private$fallbackPool;
37+
38+
/**
39+
* @param LoaderChain $loader
40+
* @param string $phpArrayFile The PHP file where metadata are cached.
41+
* @param CacheItemPoolInterface $fallbackPool The pool where runtime-discovered metadata are cached.
42+
*/
43+
publicfunction__construct(LoaderChain$loader,$phpArrayFile,CacheItemPoolInterface$fallbackPool)
44+
{
45+
$this->loader =$loader;
46+
$this->phpArrayFile =$phpArrayFile;
47+
if (!$fallbackPoolinstanceof AdapterInterface) {
48+
$fallbackPool =newProxyAdapter($fallbackPool);
49+
}
50+
$this->fallbackPool =$fallbackPool;
51+
}
52+
53+
/**
54+
* {@inheritdoc}
55+
*/
56+
publicfunctionwarmUp($cacheDir)
57+
{
58+
$adapter =newPhpArrayAdapter($this->phpArrayFile,$this->fallbackPool);
59+
$arrayPool =newArrayAdapter(0,false);
60+
61+
$metadataFactory =newCacheClassMetadataFactory(newClassMetadataFactory($this->loader),$arrayPool);
62+
63+
foreach ($this->extractSupportedLoaders(array($this->loader))as$loader) {
64+
foreach ($loader->getMappedClasses()as$mappedClass) {
65+
$metadataFactory->getMetadataFor($mappedClass);
66+
}
67+
}
68+
69+
$values =$arrayPool->getValues();
70+
$adapter->warmUp($values);
71+
72+
foreach ($valuesas$k =>$v) {
73+
$item =$this->fallbackPool->getItem($k);
74+
$this->fallbackPool->saveDeferred($item->set($v));
75+
}
76+
$this->fallbackPool->commit();
77+
}
78+
79+
/**
80+
* {@inheritdoc}
81+
*/
82+
publicfunctionisOptional()
83+
{
84+
returntrue;
85+
}
86+
87+
/**
88+
* @param LoaderInterface[] $loaders
89+
*
90+
* @return XmlFileLoader[]|YamlFileLoader[]
91+
*/
92+
privatefunctionextractSupportedLoaders(array$loaders)
93+
{
94+
$supportedLoaders =array();
95+
96+
foreach ($loadersas$loader) {
97+
if ($loaderinstanceof XmlFileLoader ||$loaderinstanceof YamlFileLoader) {
98+
$supportedLoaders[] =$loader;
99+
}elseif ($loaderinstanceof LoaderChain) {
100+
$supportedLoaders =array_merge($supportedLoaders,$this->extractSupportedLoaders($loader->getDelegatedLoaders()));
101+
}
102+
}
103+
104+
return$supportedLoaders;
105+
}
106+
}

‎src/Symfony/Bundle/FrameworkBundle/DependencyInjection/FrameworkExtension.php‎

Lines changed: 12 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,7 @@
1313

1414
useDoctrine\Common\Annotations\Reader;
1515
useSymfony\Component\Cache\Adapter\AdapterInterface;
16+
useSymfony\Component\Cache\DoctrineProvider;
1617
useSymfony\Component\DependencyInjection\ContainerBuilder;
1718
useSymfony\Component\DependencyInjection\ContainerInterface;
1819
useSymfony\Component\DependencyInjection\Definition;
@@ -1068,23 +1069,29 @@ private function registerSerializerConfiguration(array $config, ContainerBuilder
10681069

10691070
$chainLoader->replaceArgument(0,$serializerLoaders);
10701071

1072+
$cache =null;
1073+
10711074
if (isset($config['cache']) &&$config['cache']) {
10721075
@trigger_error('The "framework.serializer.cache" option is deprecated since Symfony 3.1 and will be removed in 4.0. Configure the "cache.serializer" service under "framework.cache.pools" instead.',E_USER_DEPRECATED);
10731076

1077+
$cache =newDefinition(DoctrineProvider::class);
1078+
$cache->setDecoratedService($config['cache']);
1079+
$cache->setPublic(false);
1080+
}elseif (!$container->getParameter('kernel.debug')) {
1081+
$cache =newReference('serializer.mapping.cache.symfony');
1082+
}
1083+
1084+
if ($cache) {
10741085
$container->setParameter(
10751086
'serializer.mapping.cache.prefix',
10761087
'serializer_'.$this->getKernelRootHash($container)
10771088
);
10781089

1079-
$container->getDefinition('serializer.mapping.class_metadata_factory')->replaceArgument(
1080-
1,newReference($config['cache'])
1081-
);
1082-
}elseif (!$container->getParameter('kernel.debug')) {
10831090
$cacheMetadataFactory =newDefinition(
10841091
CacheClassMetadataFactory::class,
10851092
array(
10861093
newReference('serializer.mapping.cache_class_metadata_factory.inner'),
1087-
newReference('cache.serializer'),
1094+
$cache,
10881095
)
10891096
);
10901097
$cacheMetadataFactory->setPublic(false);

‎src/Symfony/Bundle/FrameworkBundle/Resources/config/serializer.xml‎

Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -39,6 +39,19 @@
3939
</service>
4040

4141
<!-- Cache-->
42+
<serviceid="serializer.mapping.cache_warmer"class="Symfony\Bundle\FrameworkBundle\CacheWarmer\SerializerCacheWarmer"public="false">
43+
<argumenttype="service"id="serializer.mapping.chain_loader" />
44+
<argument>%serializer.mapping.cache.file%</argument>
45+
<argumenttype="service"id="cache.serializer" />
46+
<tagname="kernel.cache_warmer" />
47+
</service>
48+
49+
<serviceid="serializer.mapping.cache.symfony"class="Symfony\Component\Cache\Adapter\PhpArrayAdapter">
50+
<factoryclass="Symfony\Component\Cache\Adapter\PhpArrayAdapter"method="create" />
51+
<argument>%serializer.mapping.cache.file%</argument>
52+
<argumenttype="service"id="cache.serializer" />
53+
</service>
54+
4255
<serviceid="serializer.mapping.cache.doctrine.apc"class="Doctrine\Common\Cache\ApcCache"public="false">
4356
<callmethod="setNamespace">
4457
<argument>%serializer.mapping.cache.prefix%</argument>
Lines changed: 77 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,77 @@
1+
<?php
2+
3+
/*
4+
* This file is part of the Symfony package.
5+
*
6+
* (c) Fabien Potencier <fabien@symfony.com>
7+
*
8+
* For the full copyright and license information, please view the LICENSE
9+
* file that was distributed with this source code.
10+
*/
11+
12+
namespaceSymfony\Bundle\FrameworkBundle\Tests\CacheWarmer;
13+
14+
useSymfony\Bundle\FrameworkBundle\CacheWarmer\SerializerCacheWarmer;
15+
useSymfony\Bundle\FrameworkBundle\Tests\TestCase;
16+
useSymfony\Component\Cache\Adapter\ArrayAdapter;
17+
useSymfony\Component\Serializer\Mapping\Loader\LoaderChain;
18+
useSymfony\Component\Serializer\Mapping\Loader\XmlFileLoader;
19+
useSymfony\Component\Serializer\Mapping\Loader\YamlFileLoader;
20+
21+
class SerializerCacheWarmerTestextends TestCase
22+
{
23+
publicfunctiontestWarmUp()
24+
{
25+
$loader =newLoaderChain(array(
26+
newXmlFileLoader(__DIR__.'/../Fixtures/Serialization/Resources/person.xml'),
27+
newYamlFileLoader(__DIR__.'/../Fixtures/Serialization/Resources/author.yml'),
28+
));
29+
30+
$file =sys_get_temp_dir().'/cache-serializer.php';
31+
@unlink($file);
32+
33+
$fallbackPool =newArrayAdapter();
34+
35+
$warmer =newSerializerCacheWarmer($loader,$file,$fallbackPool);
36+
$warmer->warmUp(dirname($file));
37+
38+
$this->assertFileExists($file);
39+
40+
$values =require$file;
41+
42+
$this->assertInternalType('array',$values);
43+
$this->assertCount(2,$values);
44+
$this->assertArrayHasKey('Symfony_Bundle_FrameworkBundle_Tests_Fixtures_Serialization_Person',$values);
45+
$this->assertArrayHasKey('Symfony_Bundle_FrameworkBundle_Tests_Fixtures_Serialization_Author',$values);
46+
47+
$values =$fallbackPool->getValues();
48+
49+
$this->assertInternalType('array',$values);
50+
$this->assertCount(2,$values);
51+
$this->assertArrayHasKey('Symfony_Bundle_FrameworkBundle_Tests_Fixtures_Serialization_Person',$values);
52+
$this->assertArrayHasKey('Symfony_Bundle_FrameworkBundle_Tests_Fixtures_Serialization_Author',$values);
53+
}
54+
55+
publicfunctiontestWarmUpWithoutLoader()
56+
{
57+
$file =sys_get_temp_dir().'/cache-serializer-without-loader.php';
58+
@unlink($file);
59+
60+
$fallbackPool =newArrayAdapter();
61+
62+
$warmer =newSerializerCacheWarmer(newLoaderChain(array()),$file,$fallbackPool);
63+
$warmer->warmUp(dirname($file));
64+
65+
$this->assertFileExists($file);
66+
67+
$values =require$file;
68+
69+
$this->assertInternalType('array',$values);
70+
$this->assertCount(0,$values);
71+
72+
$values =$fallbackPool->getValues();
73+
74+
$this->assertInternalType('array',$values);
75+
$this->assertCount(0,$values);
76+
}
77+
}

‎src/Symfony/Bundle/FrameworkBundle/Tests/DependencyInjection/FrameworkExtensionTest.php‎

Lines changed: 23 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,7 @@
2121
useSymfony\Component\Cache\Adapter\ProxyAdapter;
2222
useSymfony\Component\Cache\Adapter\RedisAdapter;
2323
useSymfony\Component\DependencyInjection\ContainerBuilder;
24+
useSymfony\Component\DependencyInjection\Definition;
2425
useSymfony\Component\DependencyInjection\DefinitionDecorator;
2526
useSymfony\Component\DependencyInjection\Loader\ClosureLoader;
2627
useSymfony\Component\DependencyInjection\ParameterBag\ParameterBag;
@@ -467,7 +468,7 @@ public function testSerializerEnabled()
467468

468469
$this->assertCount(1,$argument);
469470
$this->assertEquals('Symfony\Component\Serializer\Mapping\Loader\AnnotationLoader',$argument[0]->getClass());
470-
$this->assertNull($container->getDefinition('serializer.mapping.class_metadata_factory')->getArgument(1));
471+
$this->assertNull($container->getDefinition('serializer.mapping.raw_class_metadata_factory')->getArgument(1));
471472
$this->assertEquals(newReference('serializer.name_converter.camel_case_to_snake_case'),$container->getDefinition('serializer.normalizer.object')->getArgument(1));
472473
$this->assertEquals(newReference('property_info', ContainerBuilder::IGNORE_ON_INVALID_REFERENCE),$container->getDefinition('serializer.normalizer.object')->getArgument(3));
473474
}
@@ -543,13 +544,23 @@ public function testObjectNormalizerRegistered()
543544
publicfunctiontestSerializerCacheActivated()
544545
{
545546
$container =$this->createContainerFromFile('serializer_enabled');
547+
546548
$this->assertTrue($container->hasDefinition('serializer.mapping.cache_class_metadata_factory'));
549+
$this->assertSame(
550+
'serializer.mapping.cache_class_metadata_factory',
551+
(string)$container->getAlias('serializer.mapping.class_metadata_factory')
552+
);
547553
}
548554

549555
publicfunctiontestSerializerCacheDisabled()
550556
{
551557
$container =$this->createContainerFromFile('serializer_enabled',array('kernel.debug' =>true,'kernel.container_class' =>__CLASS__));
552-
$this->assertFalse($container->hasDefinition('serializer.mapping.cache_class_metadata_factory'));
558+
559+
$this->assertTrue($container->hasDefinition('serializer.mapping.cache_class_metadata_factory'));
560+
$this->assertSame(
561+
'serializer.mapping.raw_class_metadata_factory',
562+
(string)$container->getAlias('serializer.mapping.class_metadata_factory')
563+
);
553564
}
554565

555566
/**
@@ -561,8 +572,16 @@ public function testDeprecatedSerializerCacheOption()
561572
ErrorAssert::assertDeprecationsAreTriggered('The "framework.serializer.cache" option is deprecated',function () {
562573
$container =$this->createContainerFromFile('serializer_legacy_cache',array('kernel.debug' =>true,'kernel.container_class' =>__CLASS__));
563574

564-
$this->assertFalse($container->hasDefinition('serializer.mapping.cache_class_metadata_factory'));
565-
$this->assertEquals(newReference('foo'),$container->getDefinition('serializer.mapping.class_metadata_factory')->getArgument(1));
575+
$this->assertTrue($container->hasDefinition('serializer.mapping.cache_class_metadata_factory'));
576+
$this->assertSame(
577+
'serializer.mapping.cache_class_metadata_factory',
578+
(string)$container->getAlias('serializer.mapping.class_metadata_factory')
579+
);
580+
581+
$cachedDefinition =$container->getDefinition('serializer.mapping.cache_class_metadata_factory');
582+
583+
$this->assertInstanceOf(Definition::class,$cachedDefinition->getArgument(1));
584+
$this->assertSame('foo',$cachedDefinition->getArgument(1)->getDecoratedService()[0]);
566585
});
567586
}
568587

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
<?php
2+
3+
namespaceSymfony\Bundle\FrameworkBundle\Tests\Fixtures\Serialization;
4+
5+
class Author
6+
{
7+
public$gender;
8+
}
Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
<?php
2+
3+
namespaceSymfony\Bundle\FrameworkBundle\Tests\Fixtures\Serialization;
4+
5+
class Person
6+
{
7+
public$gender;
8+
}
Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,4 @@
1+
Symfony\Bundle\FrameworkBundle\Tests\Fixtures\Serialization\Author:
2+
attributes:
3+
gender:
4+
groups:['group1', 'group2']
Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,13 @@
1+
<?xml version="1.0" ?>
2+
<serializerxmlns="http://symfony.com/schema/dic/serializer-mapping"
3+
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
4+
xsi:schemaLocation="http://symfony.com/schema/dic/serializer-mapping
5+
http://symfony.com/schema/dic/serializer-mapping/serializer-mapping-1.0.xsd"
6+
>
7+
<classname="Symfony\Bundle\FrameworkBundle\Tests\Fixtures\Serialization\Person">
8+
<attributename="gender">
9+
<group>group1</group>
10+
<group>group2</group>
11+
</attribute>
12+
</class>
13+
</serializer>

‎src/Symfony/Component/Serializer/Mapping/Loader/LoaderChain.php‎

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -63,4 +63,12 @@ public function loadClassMetadata(ClassMetadataInterface $metadata)
6363

6464
return$success;
6565
}
66+
67+
/**
68+
* @return LoaderInterface[]
69+
*/
70+
publicfunctiongetDelegatedLoaders()
71+
{
72+
return$this->loaders;
73+
}
6674
}

0 commit comments

Comments
 (0)

[8]ページ先頭

©2009-2025 Movatter.jp