Skip to content

Commit 033c9be

Browse files
authored
Merge pull request #1585 from schmittjoh/dnf-union-types
Do not typehint DNF union types
2 parents fa7ab39 + 1e2059e commit 033c9be

File tree

4 files changed

+99
-1
lines changed

4 files changed

+99
-1
lines changed

phpcs.xml.dist

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -107,6 +107,10 @@
107107
<exclude-pattern>tests/*</exclude-pattern>
108108
</rule>
109109

110+
<rule ref="Squiz.NamingConventions.ValidVariableName.MemberNotCamelCaps">
111+
<exclude-pattern>tests/Fixtures/TypedProperties/NotSupportedDNFTypes.php</exclude-pattern>
112+
</rule>
113+
110114
<rule ref="SlevomatCodingStandard.Commenting.DocCommentSpacing">
111115
<properties>
112116
<property name="annotationsGroups" type="array">

src/Metadata/Driver/TypedPropertiesDriver.php

Lines changed: 9 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -180,7 +180,15 @@ private function shouldTypeHintUnion(?ReflectionType $reflectionType)
180180
return false;
181181
}
182182

183-
foreach ($reflectionType->getTypes() as $type) {
183+
$types = $reflectionType->getTypes();
184+
185+
foreach ($types as $type) {
186+
if ($type instanceof \ReflectionIntersectionType) {
187+
return false;
188+
}
189+
}
190+
191+
foreach ($types as $type) {
184192
if ($this->shouldTypeHintInsideUnion($type)) {
185193
return true;
186194
}
Lines changed: 71 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,71 @@
1+
<?php
2+
3+
declare(strict_types=1);
4+
5+
namespace JMS\Serializer\Tests\Fixtures\TypedProperties;
6+
7+
/**
8+
* @link https://wiki.php.net/rfc/dnf_types
9+
* Changing this file may create some BC change.
10+
*/
11+
class NotSupportedDNFTypes
12+
{
13+
// Accepts an object that implements both A and B,
14+
// OR an object that implements D.
15+
private (A&B)|D $CandBorD;
16+
17+
// Accepts an object that implements C,
18+
// OR a child of X that also implements D,
19+
// OR null.
20+
private C|(X&D)|null $CorXandDorNULL;
21+
22+
// Accepts an object that implements all three of A, B, and D,
23+
// OR an int,
24+
// OR null.
25+
private (A&B&D)|int|null $AandBandCorINTorNULL;
26+
27+
// Accepts an object that implements both A and B,
28+
// OR an object that implements both A and D.
29+
private (A&B)|(A&D ) $AandBorAandD;
30+
31+
// Accepts an object that implements A and B,
32+
// OR an object that implements both B and D,
33+
// OR a child of W that also implements B,
34+
// OR null.
35+
private A|(B&D)|(B&W)|null $AorBandDorBandWorNULL;
36+
37+
public function __construct(
38+
private (A&B)|D $promotedCandBorD,
39+
private C|(X&D)|null $promotedCorXandDorNULL,
40+
private (A&B&D)|int|null $promotedAandBandCorINTorNULL,
41+
private (A&B)|(A&D ) $promotedAandBorAandD,
42+
private A|(B&D)|(B&W)|null $promotedAorBandDorBandWorNULL,
43+
) {
44+
}
45+
}
46+
47+
interface A
48+
{
49+
}
50+
interface B
51+
{
52+
}
53+
interface C extends A
54+
{
55+
}
56+
interface D
57+
{
58+
}
59+
60+
class W implements A
61+
{
62+
}
63+
class X implements B
64+
{
65+
}
66+
class Y implements A, B
67+
{
68+
}
69+
class Z extends Y implements C
70+
{
71+
}

tests/Metadata/Driver/UnionTypedPropertiesDriverTest.php

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,7 @@
1010
use JMS\Serializer\Metadata\Driver\NullDriver;
1111
use JMS\Serializer\Metadata\Driver\TypedPropertiesDriver;
1212
use JMS\Serializer\Naming\IdenticalPropertyNamingStrategy;
13+
use JMS\Serializer\Tests\Fixtures\TypedProperties\NotSupportedDNFTypes;
1314
use JMS\Serializer\Tests\Fixtures\TypedProperties\UnionTypedProperties;
1415
use Metadata\Driver\DriverChain;
1516
use PHPUnit\Framework\TestCase;
@@ -86,6 +87,20 @@ public function testInferUnionTypesShouldIncludeValueTypes()
8687
);
8788
}
8889

90+
public function testDNFTypes()
91+
{
92+
if (PHP_VERSION_ID < 80200) {
93+
self::markTestSkipped();
94+
}
95+
96+
$m = $this->resolve(NotSupportedDNFTypes::class);
97+
98+
self::assertCount(10, $m->propertyMetadata);
99+
foreach ($m->propertyMetadata as $propertyMetadata) {
100+
self::assertNull($propertyMetadata->type, 'Breaking Change: TypeResolved for: ' . $propertyMetadata->name);
101+
}
102+
}
103+
89104
private function resolve(string $classToResolve): ClassMetadata
90105
{
91106
$namingStrategy = new IdenticalPropertyNamingStrategy();

0 commit comments

Comments
 (0)