Skip to content

Commit 4a16514

Browse files
committed
ParametersExtension: exports both statements and dynamic parameters, preloads only the latter
1 parent a548b1c commit 4a16514

3 files changed

Lines changed: 53 additions & 11 deletions

File tree

src/DI/Extensions/ParametersExtension.php

Lines changed: 13 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -73,7 +73,6 @@ public function afterCompile(Nette\PhpGenerator\ClassType $class)
7373
->addBody('return ?;', [array_diff_key($builder->parameters, $dynamicParams)]);
7474
$class->addMember($method);
7575

76-
$dynamicParams = array_keys($dynamicParams, true, true);
7776
if (!$dynamicParams) {
7877
return;
7978
}
@@ -83,17 +82,23 @@ public function afterCompile(Nette\PhpGenerator\ClassType $class)
8382
$method = Method::from([Container::class, 'getDynamicParameter']);
8483
$class->addMember($method);
8584
$method->addBody('switch (true) {');
86-
foreach ($dynamicParams as $key) {
85+
foreach ($dynamicParams as $key => $foo) {
8786
$value = Helpers::expand($this->config[$key] ?? null, $builder->parameters);
88-
$value = $generator->convertArguments($resolver->completeArguments(Helpers::filterArguments([$value])))[0];
89-
$method->addBody("\tcase \$key === ?: return ?;", [$key, $value]);
87+
try {
88+
$value = $generator->convertArguments($resolver->completeArguments(Helpers::filterArguments([$value])))[0];
89+
$method->addBody("\tcase \$key === ?: return ?;", [$key, $value]);
90+
} catch (Nette\DI\ServiceCreationException $e) {
91+
$method->addBody("\tcase \$key === ?: throw new Nette\\DI\\ServiceCreationException(?);", [$key, $e->getMessage()]);
92+
}
9093
}
9194
$method->addBody("\tdefault: return parent::getDynamicParameter(\$key);\n};");
9295

93-
$method = Method::from([Container::class, 'getParameters']);
94-
$class->addMember($method);
95-
$method->addBody('array_map([$this, \'getParameter\'], ?);', [$dynamicParams]);
96-
$method->addBody('return parent::getParameters();');
96+
if ($preload = array_keys($dynamicParams, true, true)) {
97+
$method = Method::from([Container::class, 'getParameters']);
98+
$class->addMember($method);
99+
$method->addBody('array_map([$this, \'getParameter\'], ?);', [$preload]);
100+
$method->addBody('return parent::getParameters();');
101+
}
97102

98103
foreach ($this->dynamicValidators as [$param, $expected, $path]) {
99104
if ($param instanceof DynamicParameter) {

tests/DI/Compiler.parameters.phpt

Lines changed: 33 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -41,9 +41,7 @@ test('Statement as parameter', function () {
4141

4242
Assert::same([], $container->parameters);
4343
Assert::same([], $container->getParameters());
44-
Assert::exception(function () use ($container) {
45-
$container->getParameter('bar');
46-
}, Nette\InvalidStateException::class, "Parameter 'bar' not found. Check if 'di › export › parameters' is enabled.");
44+
Assert::same('a', $container->getParameter('bar'));
4745
Assert::same('a', $container->getService('one')->arg);
4846
});
4947

@@ -157,3 +155,35 @@ test('Not circular reference', function () {
157155
$container->getParameters()
158156
);
159157
});
158+
159+
160+
test('Invalid statement as parameter', function () {
161+
$compiler = new DI\Compiler;
162+
$container = createContainer($compiler, '
163+
parameters:
164+
bar: unknown()
165+
');
166+
167+
Assert::same([], $container->getParameters());
168+
Assert::exception(
169+
function () use ($container) { $container->getParameter('bar'); },
170+
Nette\DI\ServiceCreationException::class,
171+
"Class 'unknown' not found."
172+
);
173+
});
174+
175+
176+
test('Invalid statement as parameter', function () {
177+
$compiler = new DI\Compiler;
178+
$container = createContainer($compiler, '
179+
parameters:
180+
bar: Service::unknown()
181+
');
182+
183+
Assert::same([], $container->getParameters());
184+
Assert::exception(
185+
function () use ($container) { $container->getParameter('bar'); },
186+
Error::class,
187+
'Call to undefined method Service::unknown()'
188+
);
189+
});

tests/DI/expected/compiler.parameters.php

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -41,12 +41,19 @@ protected function getDynamicParameter($key)
4141
'inner' => $this->getParameter('dynamic')['foo'],
4242
'expr' => trim(' a '),
4343
];
44+
case $key === 'expr': return trim(' a ');
45+
case $key === 'arrayExpr': return ['expr' => trim(' a ')];
46+
case $key === 'arrayExpr2': return ['expr' => trim(' a ')];
4447
case $key === 'arrayDynamic': return [
4548
'dynamic' => $this->getParameter('dynamic'),
4649
'inner' => $this->getParameter('dynamic')['foo'],
4750
];
51+
case $key === 'arrayMix': return ['expr' => trim(' a '), 'dynamic' => $this->getParameter('dynamic')];
4852
case $key === 'refDynamic': return $this->getParameter('dynamic');
4953
case $key === 'refDynamic2': return $this->getParameter('dynamic')['foo'];
54+
case $key === 'refExpr': return trim(' a ');
55+
case $key === 'refArrayE1': return ['expr' => trim(' a ')];
56+
case $key === 'refArrayE2': return trim(' a ');
5057
case $key === 'refArrayD1': return [
5158
'dynamic' => $this->getParameter('dynamic'),
5259
'inner' => $this->getParameter('dynamic')['foo'],

0 commit comments

Comments
 (0)