8000 [DependencyInjection] Fix dumping non-shared factories with TaggedIte… · symfony/symfony@a60dfcf · GitHub
[go: up one dir, main page]

Skip to content

Commit a60dfcf

Browse files
marphifabpot
authored andcommitted
[DependencyInjection] Fix dumping non-shared factories with TaggedIteratorArgument
1 parent 033dace commit a60dfcf

File tree

4 files changed

+168
-1
lines changed

4 files changed

+168
-1
lines changed

src/Symfony/Component/DependencyInjection/Dumper/PhpDumper.php

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -945,8 +945,9 @@ protected static function {$methodName}(\$container$lazyInitialization)
945945
if (!$isProxyCandidate && !$definition->isShared()) {
946946
$c = implode("\n", array_map(fn ($line) => $line ? ' '.$line : $line, explode("\n", $c)));
947947
$lazyloadInitialization = $definition->isLazy() ? ', $lazyLoad = true' : '';
948+
$useContainerRef = $this->addContainerRef ? ' use ($containerRef)' : '';
948949

949-
$c = sprintf(" %s = function (\$container%s) {\n%s };\n\n return %1\$s(\$container);\n", $factory, $lazyloadInitialization, $c);
950+
$c = sprintf(" %s = function (\$container%s)%s {\n%s };\n\n return %1\$s(\$container);\n", $factory, $lazyloadInitialization, $useContainerRef, $c);
950951
}
951952

952953
$code .= $c;

src/Symfony/Component/DependencyInjection/Tests/Dumper/PhpDumperTest.php

Lines changed: 30 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,7 @@
2121
use Symfony\Component\DependencyInjection\Argument\ServiceClosureArgument;
2222
use Symfony\Component\DependencyInjection\Argument\ServiceLocator as ArgumentServiceLocator;
2323
use Symfony\Component\DependencyInjection\Argument\ServiceLocatorArgument;
24+
use Symfony\Component\DependencyInjection\Argument\TaggedIteratorArgument;
2425
use Symfony\Component\DependencyInjection\Attribute\Autowire;
2526
use Symfony\Component\DependencyInjection\Attribute\AutowireCallable;
2627
use Symfony\Component\DependencyInjection\Attribute\AutowireServiceClosure;
@@ -285,6 +286,35 @@ public function testDumpAsFilesWithFactoriesInlined()
285286
$this->assertStringMatchesFormatFile(self::$fixturesPath.'/php/services9_inlined_factories.txt', $dump);
286287
}
287288

289+
public function testDumpAsFilesWithFactoriesInlinedWithTaggedIterator()
290+
{
291+
$container = new ContainerBuilder();
292+
$container
293+
->register('foo', FooClass::class)
294+
->addMethodCall('setOtherInstances', [new TaggedIteratorArgument('foo')])
295+
->setShared(false)
296+
->setPublic(true);
297+
298+
$container
299+
->register('Bar', 'Bar')
300+
->addTag('foo');
301+
302+
$container
303+
->register('stdClass', '\stdClass')
304+
->addTag('foo');
305+
306+
$container->compile();
307+
308+
$dumper = new PhpDumper($container);
309+
$dump = print_r($dumper->dump(['as_files' => true, 'file' => __DIR__, 'hot_path_tag' => 'hot', 'build_time' => 1563381341, 'inline_factories' => true, 'inline_class_loader' => true]), true);
310+
311+
if ('\\' === \DIRECTORY_SEPARATOR) {
312+
$dump = str_replace("'.\\DIRECTORY_SEPARATOR.'", '/', $dump);
313+
}
314+
315+
$this->assertStringMatchesFormatFile(self::$fixturesPath.'/php/services9_inlined_factories_with_tagged_iterrator.txt', $dump);
316+
}
317+
288318
public function testDumpAsFilesWithLazyFactoriesInlined()
289319
{
290320
$container = new ContainerBuilder();

src/Symfony/Component/DependencyInjection/Tests/Fixtures/includes/foo.php

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,7 @@ class FooClass
77
public $qux;
88
public $foo;
99
public $moo;
10+
public $otherInstances;
1011

1112
public $bar = null;
1213
public $initialized = false;
@@ -41,4 +42,9 @@ public function setBar($value = null)
4142
{
4243
$this->bar = $value;
4344
}
45+
46+
public function setOtherInstances($otherInstances)
47+
{
48+
$this->otherInstances = $otherInstances;
49+
}
4450
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,130 @@
1+
Array
2+
(
3+
[Container%s/removed-ids.php] => <?php
4+
5+
namespace Container%s;
6+
7+
return [
8+
'Bar' => true,
9+
'stdClass' => true,
10+
];
11+
12+
[Container%s/ProjectServiceContainer.php] => <?php
13+
14+
namespace Container%s;
15+
16+
use Symfony\Component\DependencyInjection\Argument\RewindableGenerator;
17+
use Symfony\Component\DependencyInjection\ContainerInterface;
18+
use Symfony\Component\DependencyInjection\Container;
19+
use Symfony\Component\DependencyInjection\Exception\LogicException;
20+
use Symfony\Component\DependencyInjection\Exception\ParameterNotFoundException;
21+
use Symfony\Component\DependencyInjection\Exception\RuntimeException;
22+
use Symfony\Component\DependencyInjection\ParameterBag\FrozenParameterBag;
23+
use Symfony\Component\DependencyInjection\ParameterBag\ParameterBagInterface;
24+
25+
/**
26+
* @internal This class has been auto-generated by the Symfony Dependency Injection Component.
27+
*/
28+
class ProjectServiceContainer extends Container
29+
{
30+
protected $targetDir;
31+
protected $parameters = [];
32+
protected readonly \WeakReference $ref;
33+
34+
public function __construct(private array $buildParameters = [], protected string $containerDir = __DIR__)
35+
{
36+
$this->ref = \WeakReference::create($this);
37+
$this->targetDir = \dirname($containerDir);
38+
$this->services = $this->pr F438 ivates = [];
39+
$this->methodMap = [
40+
'foo' => 'getFooService',
41+
];
42+
43+
$this->aliases = [];
44+
}
45+
46+
public function compile(): void
47+
{
48+
throw new LogicException('You cannot compile a dumped container that was already compiled.');
49+
}
50+
51+
public function isCompiled(): bool
52+
{
53+
return true;
54+
}
55+
56+
public function getRemovedIds(): array
57+
{
58+
return require $this->containerDir.\DIRECTORY_SEPARATOR.'removed-ids.php';
59+
}
60+
61+
/**
62+
* Gets the public 'foo' service.
63+
*
64+
* @return \Symfony\Component\DependencyInjection\Tests\Dumper\FooClass
65+
*/
66+
protected static function getFooService($container)
67+
{
68+
$containerRef = $container->ref;
69+
70+
$container->factories['foo'] = function ($container) use ($containerRef) {
71+
$instance = new \Symfony\Component\DependencyInjection\Tests\Dumper\FooClass();
72+
73+
$instance->setOtherInstances(new RewindableGenerator(function () use ($containerRef) {
74+
$container = $containerRef->get();
75+
76+
yield 0 => ($container->privates['Bar'] ??= new \Bar());
77+
yield 1 => ($container->privates['stdClass'] ??= new \stdClass());
78+
}, 2));
79+
80+
return $instance;
81+
};
82+
83+
return $container->factories['foo']($container);
84+
}
85+
}
86+
87+
[ProjectServiceContainer.preload.php] => <?php
88+
89+
// This file has been auto-generated by the Symfony Dependency Injection Component
90+
// You can reference it in the "opcache.preload" php.ini setting on PHP >= 7.4 when preloading is desired
91+
92+
use Symfony\Component\DependencyInjection\Dumper\Preloader;
93+
94+
if (in_array(PHP_SAPI, ['cli', 'phpdbg'], true)) {
95+
return;
96+
}
97+
98+
require dirname(__DIR__, %d).'/vendor/autoload.php';
99+
(require __DIR__.'/ProjectServiceContainer.php')->set(\Container%s\ProjectServiceContainer::class, null);
100+
101+
$classes = [];
102+
$classes[] = 'Bar';
103+
$classes[] = 'Symfony\Component\DependencyInjection\Tests\Dumper\FooClass';
104+
$classes[] = 'Symfony\Component\DependencyInjection\ContainerInterface';
105+
106+
$preloaded = Preloader::preload($classes);
107+
108+
[ProjectServiceContainer.php] => <?php
109+
110+
// This file has been auto-generated by the Symfony Dependency Injection Component for internal use.
111+
112+
if (\class_exists(\Container%s\ProjectServiceContainer::class, false)) {
113+
// no-op
114+
} elseif (!include __DIR__.'/Container%s/ProjectServiceContainer.php') {
115+
touch(__DIR__.'/Container%s.legacy');
116+
117+
return;
118+
}
119+
120+
if (!\class_exists(ProjectServiceContainer::class, false)) {
121+
\class_alias(\Container%s\ProjectServiceContainer::class, ProjectServiceContainer::class, false);
122+
}
123+
124+
return new \Container%s\ProjectServiceContainer([
125+
'container.build_hash' => '%s',
126+
'container.build_id' => '3f6e2bc2',
127+
'container.build_time' => 1563381341,
128+
], __DIR__.\DIRECTORY_SEPARATOR.'Container%s');
129+
130+
)

0 commit comments

Comments
 (0)
0