Skip to content

Commit 8fb0f58

Browse files
Merge branch '4.4' into 5.3
* 4.4: [HttpClient] Remove deprecated usage of `GuzzleHttp\Promise\queue` [PropertyAccess] Fix handling of uninitialized property of anonymous class [DependencyInjection] fix test ResolveBindingsPass remove loading of class iterable [FrameworkBundle] Avoid calling rtrim(null, '/') in AssetsInstallCommand [DependencyInjection] Fix nested env var with resolve processor Allow OutputFormatter::escape() to be used for escaping URLs used in <href> allow a zero time-limit [DependencyInjection] Ignore argument type check in CheckTypeDeclarationsPass if it's a Definition with a factory [Validators] Add translations for Slovak #43735
2 parents 66dda4e + 9b9397f commit 8fb0f58

File tree

8 files changed

+177
-3
lines changed

8 files changed

+177
-3
lines changed

Compiler/CheckTypeDeclarationsPass.php

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -210,6 +210,10 @@ private function checkType(Definition $checkedDefinition, $value, \ReflectionPar
210210
$class = null;
211211

212212
if ($value instanceof Definition) {
213+
if ($value->getFactory()) {
214+
return;
215+
}
216+
213217
$class = $value->getClass();
214218

215219
if ($class && isset(self::BUILTIN_TYPES[strtolower($class)])) {

Compiler/ResolveBindingsPass.php

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -126,7 +126,7 @@ protected function processValue($value, bool $isRoot = false)
126126
$this->unusedBindings[$bindingId] = [$key, $this->currentId, $bindingType, $file];
127127
}
128128

129-
if (preg_match('/^(?:(?:array|bool|float|int|string|([^ $]++)) )\$/', $key, $m)) {
129+
if (preg_match('/^(?:(?:array|bool|float|int|string|iterable|([^ $]++)) )\$/', $key, $m)) {
130130
$bindingNames[substr($key, \strlen($m[0]))] = $binding;
131131
}
132132

EnvVarProcessor.php

Lines changed: 8 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -272,11 +272,17 @@ public function getEnv(string $prefix, string $name, \Closure $getEnv)
272272
}
273273

274274
if ('resolve' === $prefix) {
275-
return preg_replace_callback('/%%|%([^%\s]+)%/', function ($match) use ($name) {
275+
return preg_replace_callback('/%%|%([^%\s]+)%/', function ($match) use ($name, $getEnv) {
276276
if (!isset($match[1])) {
277277
return '%';
278278
}
279-
$value = $this->container->getParameter($match[1]);
279+
280+
if (str_starts_with($match[1], 'env(') && str_ends_with($match[1], ')') && 'env()' !== $match[1]) {
281+
$value = $getEnv(substr($match[1], 4, -1));
282+
} else {
283+
$value = $this->container->getParameter($match[1]);
284+
}
285+
280286
if (!is_scalar($value)) {
281287
throw new RuntimeException(sprintf('Parameter "%s" found when resolving env var "%s" must be scalar, "%s" given.', $match[1], $name, get_debug_type($value)));
282288
}

Tests/Compiler/CheckTypeDeclarationsPassTest.php

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -996,6 +996,20 @@ public function testCallableClass()
996996

997997
$this->addToAssertionCount(1);
998998
}
999+
1000+
public function testIgnoreDefinitionFactoryArgument()
1001+
{
1002+
$container = new ContainerBuilder();
1003+
$container->register('bar', Bar::class)
1004+
->setArguments([
1005+
(new Definition(Foo::class))
1006+
->setFactory([Foo::class, 'createStdClass']),
1007+
]);
1008+
1009+
(new CheckTypeDeclarationsPass())->process($container);
1010+
1011+
$this->addToAssertionCount(1);
1012+
}
9991013
}
10001014

10011015
class CallableClass

Tests/Compiler/ResolveBindingsPassTest.php

Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -28,6 +28,7 @@
2828
use Symfony\Component\DependencyInjection\Tests\Fixtures\FooUnitEnum;
2929
use Symfony\Component\DependencyInjection\Tests\Fixtures\NamedArgumentsDummy;
3030
use Symfony\Component\DependencyInjection\Tests\Fixtures\NamedEnumArgumentDummy;
31+
use Symfony\Component\DependencyInjection\Tests\Fixtures\NamedIterableArgumentDummy;
3132
use Symfony\Component\DependencyInjection\Tests\Fixtures\ParentNotExists;
3233
use Symfony\Component\DependencyInjection\Tests\Fixtures\WithTarget;
3334
use Symfony\Component\DependencyInjection\TypedReference;
@@ -212,6 +213,28 @@ public function testEmptyBindingTypehint()
212213
$pass->process($container);
213214
}
214215

216+
public function testIterableBindingTypehint()
217+
{
218+
$autoloader = static function ($class) {
219+
if ('iterable' === $class) {
220+
throw new \RuntimeException('We should not search pseudo-type iterable as class');
221+
}
222+
};
223+
spl_autoload_register($autoloader);
224+
225+
$container = new ContainerBuilder();
226+
$definition = $container->register('bar', NamedIterableArgumentDummy::class);
227+
$definition->setBindings([
228+
'iterable $items' => new TaggedIteratorArgument('foo'),
229+
]);
230+
$pass = new ResolveBindingsPass();
231+
$pass->process($container);
232+
233+
$this->assertInstanceOf(TaggedIteratorArgument::class, $container->getDefinition('bar')->getArgument(0));
234+
235+
spl_autoload_unregister($autoloader);
236+
}
237+
215238
/**
216239
* @requires PHP 8
217240
*/

Tests/EnvVarProcessorTest.php

Lines changed: 103 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -506,6 +506,109 @@ public function testRequireFile()
506506
$this->assertEquals('foo', $result);
507507
}
508508

509+
/**
510+
* @dataProvider validResolve
511+
*/
512+
public function testGetEnvResolve($value, $processed)
513+
{
514+
$container = new ContainerBuilder();
515+
$container->setParameter('bar', $value);
516+
$container->compile();
517+
518+
$processor = new EnvVarProcessor($container);
519+
520+
$result = $processor->getEnv('resolve', 'foo', function () {
521+
return '%bar%';
522+
});
523+
524+
$this->assertSame($processed, $result);
525+
}
526+
527+
public function validResolve()
528+
{
529+
return [
530+
['string', 'string'],
531+
[1, '1'],
532+
[1.1, '1.1'],
533+
[true, '1'],
534+
[false, ''],
535+
];
536+
}
537+
538+
public function testGetEnvResolveNoMatch()
539+
{
540+
$processor = new EnvVarProcessor(new Container());
541+
542+
$result = $processor->getEnv('resolve', 'foo', function () {
543+
return '%%';
544+
});
545+
546+
$this->assertSame('%', $result);
547+
}
548+
549+
/**
550+
* @dataProvider notScalarResolve
551+
*/
552+
public function testGetEnvResolveNotScalar($value)
553+
{
554+
$this->expectException(RuntimeException::class);
555+
$this->expectExceptionMessage('Parameter "bar" found when resolving env var "foo" must be scalar');
556+
557+
$container = new ContainerBuilder();
558+
$container->setParameter('bar', $value);
559+
$container->compile();
560+
561+
$processor = new EnvVarProcessor($container);
562+
563+
$processor->getEnv('resolve', 'foo', function () {
564+
return '%bar%';
565+
});
566+
}
567+
568+
public function notScalarResolve()
569+
{
570+
return [
571+
[null],
572+
[[]],
573+
];
574+
}
575+
576+
public function testGetEnvResolveNestedEnv()
577+
{
578+
$container = new ContainerBuilder();
579+
$container->setParameter('env(BAR)', 'BAR in container');
580+
$container->compile();
581+
582+
$processor = new EnvVarProcessor($container);
583+
$getEnv = \Closure::fromCallable([$processor, 'getEnv']);
584+
585+
$result = $processor->getEnv('resolve', 'foo', function ($name) use ($getEnv) {
586+
return 'foo' === $name ? '%env(BAR)%' : $getEnv('string', $name, function () {});
587+
});
588+
589+
$this->assertSame('BAR in container', $result);
590+
}
591+
592+
public function testGetEnvResolveNestedRealEnv()
593+
{
594+
$_ENV['BAR'] = 'BAR in environment';
595+
596+
$container = new ContainerBuilder();
597+
$container->setParameter('env(BAR)', 'BAR in container');
598+
$container->compile();
599+
600+
$processor = new EnvVarProcessor($container);
601+
$getEnv = \Closure::fromCallable([$processor, 'getEnv']);
602+
603+
$result = $processor->getEnv('resolve', 'foo', function ($name) use ($getEnv) {
604+
return 'foo' === $name ? '%env(BAR)%' : $getEnv('string', $name, function () {});
605+
});
606+
607+
$this->assertSame('BAR in environment', $result);
608+
609+
unset($_ENV['BAR']);
610+
}
611+
509612
/**
510613
* @dataProvider validCsv
511614
*/

Tests/Fixtures/CheckTypeDeclarationsPass/Foo.php

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -23,4 +23,9 @@ public static function createArray(): array
2323
{
2424
return [];
2525
}
26+
27+
public static function createStdClass(): \stdClass
28+
{
29+
return new \stdClass();
30+
}
2631
}
Lines changed: 19 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,19 @@
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+
namespace Symfony\Component\DependencyInjection\Tests\Fixtures;
13+
14+
class NamedIterableArgumentDummy
15+
{
16+
public function __construct(iterable $items)
17+
{
18+
}
19+
}

0 commit comments

Comments
 (0)