Skip to content

Commit e9c80ee

Browse files
Merge branch '4.4' into 5.4
* 4.4: [PropertyInfo] CS fix [Serializer] Try all possible denormalization route with union types when ALLOW_EXTRA_ATTRIBUTES=false CS fix [Cache] Respect $save option in ChainAdapter [ExpressionLanguage] fix tests (bis) [ExpressionLanguage] fix tests [Cache] Respect $save option in ArrayAdapter [HttpKernel] Disable session tracking while collecting profiler data [MonologBridge] Fixed support of elasticsearch 7.+ in ElasticsearchLogstashHandler [DoctrineBridge] Extend type guessing on enum fields Fix for missing sender name in case with usage of the EnvelopeListener
2 parents 7ace12d + 31cbb3c commit e9c80ee

File tree

2 files changed

+69
-1
lines changed

2 files changed

+69
-1
lines changed

Normalizer/AbstractObjectNormalizer.php

Lines changed: 14 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -416,7 +416,7 @@ public function denormalize($data, string $type, string $format = null, array $c
416416
}
417417
}
418418

419-
if (!empty($extraAttributes)) {
419+
if ($extraAttributes) {
420420
throw new ExtraAttributesException($extraAttributes);
421421
}
422422

@@ -443,6 +443,7 @@ private function validateAndDenormalize(array $types, string $currentClass, stri
443443
{
444444
$expectedTypes = [];
445445
$isUnionType = \count($types) > 1;
446+
$extraAttributesException = null;
446447
foreach ($types as $type) {
447448
if (null === $data && $type->isNullable()) {
448449
return null;
@@ -578,9 +579,21 @@ private function validateAndDenormalize(array $types, string $currentClass, stri
578579
if (!$isUnionType) {
579580
throw $e;
580581
}
582+
} catch (ExtraAttributesException $e) {
583+
if (!$isUnionType) {
584+
throw $e;
585+
}
586+
587+
if (!$extraAttributesException) {
588+
$extraAttributesException = $e;
589+
}
581590
}
582591
}
583592

593+
if ($extraAttributesException) {
594+
throw $extraAttributesException;
595+
}
596+
584597
if ($context[self::DISABLE_TYPE_ENFORCEMENT] ?? $this->defaultContext[self::DISABLE_TYPE_ENFORCEMENT] ?? false) {
585598
return $data;
586599
}

Tests/SerializerTest.php

Lines changed: 55 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,7 @@
2020
use Symfony\Component\Serializer\Encoder\DecoderInterface;
2121
use Symfony\Component\Serializer\Encoder\EncoderInterface;
2222
use Symfony\Component\Serializer\Encoder\JsonEncoder;
23+
use Symfony\Component\Serializer\Exception\ExtraAttributesException;
2324
use Symfony\Component\Serializer\Exception\InvalidArgumentException;
2425
use Symfony\Component\Serializer\Exception\LogicException;
2526
use Symfony\Component\Serializer\Exception\NotNormalizableValueException;
@@ -32,6 +33,7 @@
3233
use Symfony\Component\Serializer\Mapping\Factory\ClassMetadataFactory;
3334
use Symfony\Component\Serializer\Mapping\Factory\ClassMetadataFactoryInterface;
3435
use Symfony\Component\Serializer\Mapping\Loader\AnnotationLoader;
36+
use Symfony\Component\Serializer\Normalizer\AbstractNormalizer;
3537
use Symfony\Component\Serializer\Normalizer\AbstractObjectNormalizer;
3638
use Symfony\Component\Serializer\Normalizer\ArrayDenormalizer;
3739
use Symfony\Component\Serializer\Normalizer\CustomNormalizer;
@@ -751,6 +753,35 @@ public function testUnionTypeDeserializable()
751753
$this->assertEquals(new DummyUnionType(), $actual, 'Union type denormalization third case failed.');
752754
}
753755

756+
public function testUnionTypeDeserializableWithoutAllowedExtraAttributes()
757+
{
758+
$classMetadataFactory = new ClassMetadataFactory(new AnnotationLoader(new AnnotationReader()));
759+
$extractor = new PropertyInfoExtractor([], [new PhpDocExtractor(), new ReflectionExtractor()]);
760+
$serializer = new Serializer(
761+
[
762+
new ObjectNormalizer($classMetadataFactory, null, null, $extractor, new ClassDiscriminatorFromClassMetadata($classMetadataFactory)),
763+
],
764+
['json' => new JsonEncoder()]
765+
);
766+
767+
$actual = $serializer->deserialize('{ "v": { "a": 0 }}', DummyUnionWithAAndB::class, 'json', [
768+
AbstractNormalizer::ALLOW_EXTRA_ATTRIBUTES => false,
769+
]);
770+
771+
$this->assertEquals(new DummyUnionWithAAndB(new DummyATypeForUnion()), $actual);
772+
773+
$actual = $serializer->deserialize('{ "v": { "b": 1 }}', DummyUnionWithAAndB::class, 'json', [
774+
AbstractNormalizer::ALLOW_EXTRA_ATTRIBUTES => false,
775+
]);
776+
777+
$this->assertEquals(new DummyUnionWithAAndB(new DummyBTypeForUnion()), $actual);
778+
779+
$this->expectException(ExtraAttributesException::class);
780+
$serializer->deserialize('{ "v": { "b": 1, "c": "i am not allowed" }}', DummyUnionWithAAndB::class, 'json', [
781+
AbstractNormalizer::ALLOW_EXTRA_ATTRIBUTES => false,
782+
]);
783+
}
784+
754785
/**
755786
* @requires PHP 8.2
756787
*/
@@ -1221,6 +1252,30 @@ public function setChanged($changed): self
12211252
}
12221253
}
12231254

1255+
class DummyATypeForUnion
1256+
{
1257+
public $a = 0;
1258+
}
1259+
1260+
class DummyBTypeForUnion
1261+
{
1262+
public $b = 1;
1263+
}
1264+
1265+
class DummyUnionWithAAndB
1266+
{
1267+
/** @var DummyATypeForUnion|DummyBTypeForUnion */
1268+
public $v;
1269+
1270+
/**
1271+
* @param DummyATypeForUnion|DummyBTypeForUnion $v
1272+
*/
1273+
public function __construct($v)
1274+
{
1275+
$this->v = $v;
1276+
}
1277+
}
1278+
12241279
class Baz
12251280
{
12261281
public $list;

0 commit comments

Comments
 (0)