Skip to content

Commit adffe0c

Browse files
committed
Merge branch '3.4' into 4.4
* 3.4: Fix wrong namespaces [Validator] Fixed calling getters before resolving groups [HttpKernel][LoggerDataCollector] Prevent keys collisions in the sanitized logs processing
2 parents 2bf1de9 + 00d1696 commit adffe0c

File tree

5 files changed

+102
-3
lines changed

5 files changed

+102
-3
lines changed

Context/ExecutionContext.php

Lines changed: 7 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,7 @@
2121
use Symfony\Component\Validator\Mapping\MetadataInterface;
2222
use Symfony\Component\Validator\Mapping\PropertyMetadataInterface;
2323
use Symfony\Component\Validator\Util\PropertyPath;
24+
use Symfony\Component\Validator\Validator\LazyProperty;
2425
use Symfony\Component\Validator\Validator\ValidatorInterface;
2526
use Symfony\Component\Validator\Violation\ConstraintViolationBuilder;
2627
use Symfony\Component\Validator\Violation\ConstraintViolationBuilderInterface;
@@ -192,7 +193,7 @@ public function addViolation($message, array $parameters = [])
192193
$parameters,
193194
$this->root,
194195
$this->propertyPath,
195-
$this->value,
196+
$this->getValue(),
196197
null,
197198
null,
198199
$this->constraint
@@ -211,7 +212,7 @@ public function buildViolation($message, array $parameters = []): ConstraintViol
211212
$parameters,
212213
$this->root,
213214
$this->propertyPath,
214-
$this->value,
215+
$this->getValue(),
215216
$this->translator,
216217
$this->translationDomain
217218
);
@@ -246,6 +247,10 @@ public function getRoot()
246247
*/
247248
public function getValue()
248249
{
250+
if ($this->value instanceof LazyProperty) {
251+
return $this->value->getPropertyValue();
252+
}
253+
249254
return $this->value;
250255
}
251256

Lines changed: 27 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,27 @@
1+
<?php
2+
3+
/*
4+
* This file is part of the Symfony package.
5+
*
6+
* (c) Fabien Potencier <[email protected]>
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\Validator\Tests\Fixtures;
13+
14+
class EntityWithGroupedConstraintOnMethods
15+
{
16+
public $bar;
17+
18+
public function isValidInFoo()
19+
{
20+
return false;
21+
}
22+
23+
public function getBar()
24+
{
25+
throw new \Exception('Should not be called');
26+
}
27+
}

Tests/Validator/RecursiveValidatorTest.php

Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -14,14 +14,19 @@
1414
use Symfony\Component\Translation\IdentityTranslator;
1515
use Symfony\Component\Validator\Constraints\All;
1616
use Symfony\Component\Validator\Constraints\Collection;
17+
use Symfony\Component\Validator\Constraints\GroupSequence;
18+
use Symfony\Component\Validator\Constraints\IsTrue;
1719
use Symfony\Component\Validator\Constraints\Length;
1820
use Symfony\Component\Validator\Constraints\NotBlank;
21+
use Symfony\Component\Validator\Constraints\NotNull;
1922
use Symfony\Component\Validator\ConstraintValidatorFactory;
2023
use Symfony\Component\Validator\Context\ExecutionContextFactory;
24+
use Symfony\Component\Validator\Mapping\ClassMetadata;
2125
use Symfony\Component\Validator\Mapping\Factory\MetadataFactoryInterface;
2226
use Symfony\Component\Validator\Tests\Constraints\Fixtures\ChildA;
2327
use Symfony\Component\Validator\Tests\Constraints\Fixtures\ChildB;
2428
use Symfony\Component\Validator\Tests\Fixtures\Entity;
29+
use Symfony\Component\Validator\Tests\Fixtures\EntityWithGroupedConstraintOnMethods;
2530
use Symfony\Component\Validator\Validator\RecursiveValidator;
2631
use Symfony\Component\Validator\Validator\ValidatorInterface;
2732

@@ -118,6 +123,25 @@ public function testCollectionConstraintValidateAllGroupsForNestedConstraints()
118123
$this->assertInstanceOf(NotBlank::class, $violations->get(1)->getConstraint());
119124
}
120125

126+
public function testGroupedMethodConstraintValidateInSequence()
127+
{
128+
$metadata = new ClassMetadata(EntityWithGroupedConstraintOnMethods::class);
129+
$metadata->addPropertyConstraint('bar', new NotNull(['groups' => 'Foo']));
130+
$metadata->addGetterMethodConstraint('validInFoo', 'isValidInFoo', new IsTrue(['groups' => 'Foo']));
131+
$metadata->addGetterMethodConstraint('bar', 'getBar', new NotNull(['groups' => 'Bar']));
132+
133+
$this->metadataFactory->addMetadata($metadata);
134+
135+
$entity = new EntityWithGroupedConstraintOnMethods();
136+
$groups = new GroupSequence(['EntityWithGroupedConstraintOnMethods', 'Foo', 'Bar']);
137+
138+
$violations = $this->validator->validate($entity, null, $groups);
139+
140+
$this->assertCount(2, $violations);
141+
$this->assertInstanceOf(NotNull::class, $violations->get(0)->getConstraint());
142+
$this->assertInstanceOf(IsTrue::class, $violations->get(1)->getConstraint());
143+
}
144+
121145
public function testAllConstraintValidateAllGroupsForNestedConstraints()
122146
{
123147
$this->metadata->addPropertyConstraint('data', new All(['constraints' => [

Validator/LazyProperty.php

Lines changed: 32 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,32 @@
1+
<?php
2+
3+
/*
4+
* This file is part of the Symfony package.
5+
*
6+
* (c) Fabien Potencier <[email protected]>
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\Validator\Validator;
13+
14+
/**
15+
* A wrapper for a callable initializing a property from a getter.
16+
*
17+
* @internal
18+
*/
19+
class LazyProperty
20+
{
21+
private $propertyValueCallback;
22+
23+
public function __construct(\Closure $propertyValueCallback)
24+
{
25+
$this->propertyValueCallback = $propertyValueCallback;
26+
}
27+
28+
public function getPropertyValue()
29+
{
30+
return \call_user_func($this->propertyValueCallback);
31+
}
32+
}

Validator/RecursiveContextualValidator.php

Lines changed: 12 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -28,6 +28,7 @@
2828
use Symfony\Component\Validator\Mapping\ClassMetadataInterface;
2929
use Symfony\Component\Validator\Mapping\Factory\MetadataFactoryInterface;
3030
use Symfony\Component\Validator\Mapping\GenericMetadata;
31+
use Symfony\Component\Validator\Mapping\GetterMetadata;
3132
use Symfony\Component\Validator\Mapping\MetadataInterface;
3233
use Symfony\Component\Validator\Mapping\PropertyMetadataInterface;
3334
use Symfony\Component\Validator\Mapping\TraversalStrategy;
@@ -506,7 +507,13 @@ private function validateClassNode($object, ?string $cacheKey, ClassMetadataInte
506507
throw new UnsupportedMetadataException(sprintf('The property metadata instances should implement "Symfony\Component\Validator\Mapping\PropertyMetadataInterface", got: "%s".', \is_object($propertyMetadata) ? \get_class($propertyMetadata) : \gettype($propertyMetadata)));
507508
}
508509

509-
$propertyValue = $propertyMetadata->getPropertyValue($object);
510+
if ($propertyMetadata instanceof GetterMetadata) {
511+
$propertyValue = new LazyProperty(static function () use ($propertyMetadata, $object) {
512+
return $propertyMetadata->getPropertyValue($object);
513+
});
514+
} else {
515+
$propertyValue = $propertyMetadata->getPropertyValue($object);
516+
}
510517

511518
$this->validateGenericNode(
512519
$propertyValue,
@@ -739,6 +746,10 @@ private function validateInGroup($value, ?string $cacheKey, MetadataInterface $m
739746
$validator = $this->validatorFactory->getInstance($constraint);
740747
$validator->initialize($context);
741748

749+
if ($value instanceof LazyProperty) {
750+
$value = $value->getPropertyValue();
751+
}
752+
742753
try {
743754
$validator->validate($value, $constraint);
744755
} catch (UnexpectedValueException $e) {

0 commit comments

Comments
 (0)