Skip to content

Commit 80e5a7f

Browse files
committed
feature #37559 [PropertyInfo] fix array types with keys (array<string, string>) (digilist)
This PR was merged into the 5.2-dev branch. Discussion ---------- [PropertyInfo] fix array types with keys (array<string, string>) | Q | A | ------------- | --- | Branch? | master | Bug fix? | no | New feature? | yes | Deprecations? | no | Tickets | n/a | License | MIT | Doc PR | n/a Array types with keys are currently not detected correctly from the PropertyInfo component: ``` @var array<string, string> @var array<string, array<integer, string>> ``` Those are currently identified as object with class `rray<string, string>`. This PR tries to fix it. What I noticed while fixing this, is that union types in arrays are not supported in general at the moment, because the `Type` class supports only one collectionValueType and I do not see how to pass a Union Type there. But I guess that's a different issue and for those types I decided to return null as collection value type for now. (Or better throw on exception?) Commits ------- 64f7bd7 [PropertyInfo] fix array types with keys (array<string, string>)
2 parents 908ca44 + 64f7bd7 commit 80e5a7f

File tree

4 files changed

+66
-5
lines changed

4 files changed

+66
-5
lines changed

src/Symfony/Component/PropertyInfo/Tests/Extractor/PhpDocExtractorTest.php

Lines changed: 33 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -150,6 +150,39 @@ public function provideCollectionTypes()
150150
null,
151151
null,
152152
],
153+
[
154+
'arrayWithKeys',
155+
[new Type(
156+
Type::BUILTIN_TYPE_ARRAY,
157+
false,
158+
null,
159+
true,
160+
new Type(Type::BUILTIN_TYPE_STRING),
161+
new Type(Type::BUILTIN_TYPE_STRING)
162+
)],
163+
null,
164+
null,
165+
],
166+
[
167+
'arrayWithKeysAndComplexValue',
168+
[new Type(
169+
Type::BUILTIN_TYPE_ARRAY,
170+
false,
171+
null,
172+
true,
173+
new Type(Type::BUILTIN_TYPE_STRING),
174+
new Type(
175+
Type::BUILTIN_TYPE_ARRAY,
176+
true,
177+
null,
178+
true,
179+
new Type(Type::BUILTIN_TYPE_INT),
180+
new Type(Type::BUILTIN_TYPE_STRING, true)
181+
)
182+
)],
183+
null,
184+
null,
185+
],
153186
];
154187
}
155188

src/Symfony/Component/PropertyInfo/Tests/Extractor/ReflectionExtractorTest.php

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -63,6 +63,8 @@ public function testGetProperties()
6363
'iteratorCollection',
6464
'iteratorCollectionWithKey',
6565
'nestedIterators',
66+
'arrayWithKeys',
67+
'arrayWithKeysAndComplexValue',
6668
'foo',
6769
'foo2',
6870
'foo3',
@@ -111,6 +113,8 @@ public function testGetPropertiesWithCustomPrefixes()
111113
'iteratorCollection',
112114
'iteratorCollectionWithKey',
113115
'nestedIterators',
116+
'arrayWithKeys',
117+
'arrayWithKeysAndComplexValue',
114118
'foo',
115119
'foo2',
116120
'foo3',
@@ -149,6 +153,8 @@ public function testGetPropertiesWithNoPrefixes()
149153
'iteratorCollection',
150154
'iteratorCollectionWithKey',
151155
'nestedIterators',
156+
'arrayWithKeys',
157+
'arrayWithKeysAndComplexValue',
152158
'foo',
153159
'foo2',
154160
'foo3',

src/Symfony/Component/PropertyInfo/Tests/Fixtures/Dummy.php

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -130,6 +130,16 @@ class Dummy extends ParentDummy
130130
*/
131131
public $nestedIterators;
132132

133+
/**
134+
* @var array<string,string>
135+
*/
136+
public $arrayWithKeys;
137+
138+
/**
139+
* @var array<string,array<integer,null|string>|null>
140+
*/
141+
public $arrayWithKeysAndComplexValue;
142+
133143
public static function getStatic()
134144
{
135145
}

src/Symfony/Component/PropertyInfo/Util/PhpDocTypeHelper.php

Lines changed: 17 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,7 @@
1212
namespace Symfony\Component\PropertyInfo\Util;
1313

1414
use phpDocumentor\Reflection\Type as DocType;
15+
use phpDocumentor\Reflection\Types\Array_;
1516
use phpDocumentor\Reflection\Types\Collection;
1617
use phpDocumentor\Reflection\Types\Compound;
1718
use phpDocumentor\Reflection\Types\Null_;
@@ -109,12 +110,23 @@ private function createType(DocType $type, bool $nullable, string $docType = nul
109110
}
110111

111112
if ('[]' === substr($docType, -2)) {
112-
if ('mixed[]' === $docType) {
113-
$collectionKeyType = null;
113+
$collectionKeyType = new Type(Type::BUILTIN_TYPE_INT);
114+
$collectionValueType = $this->createType($type, false, substr($docType, 0, -2));
115+
116+
return new Type(Type::BUILTIN_TYPE_ARRAY, $nullable, null, true, $collectionKeyType, $collectionValueType);
117+
}
118+
119+
if (0 === strpos($docType, 'array<') && $type instanceof Array_) {
120+
// array<value> is converted to x[] which is handled above
121+
// so it's only necessary to handle array<key, value> here
122+
$collectionKeyType = $this->getTypes($type->getKeyType())[0];
123+
124+
$collectionValueTypes = $this->getTypes($type->getValueType());
125+
if (\count($collectionValueTypes) > 1) {
126+
// the Type class does not support union types yet, so assume that no type was defined
114127
$collectionValueType = null;
115128
} else {
116-
$collectionKeyType = new Type(Type::BUILTIN_TYPE_INT);
117-
$collectionValueType = $this->createType($type, false, substr($docType, 0, -2));
129+
$collectionValueType = $collectionValueTypes[0];
118130
}
119131

120132
return new Type(Type::BUILTIN_TYPE_ARRAY, $nullable, null, true, $collectionKeyType, $collectionValueType);
@@ -160,6 +172,6 @@ private function getPhpTypeAndClass(string $docType): array
160172
return [$docType, null];
161173
}
162174

163-
return ['object', substr($docType, 1)];
175+
return ['object', substr($docType, 1)]; // substr to strip the namespace's `\`-prefix
164176
}
165177
}

0 commit comments

Comments
 (0)
pFad - Phonifier reborn

Pfad - The Proxy pFad of © 2024 Garber Painting. All rights reserved.

Note: This service is not intended for secure transactions such as banking, social media, email, or purchasing. Use at your own risk. We assume no liability whatsoever for broken pages.


Alternative Proxies:

Alternative Proxy

pFad Proxy

pFad v3 Proxy

pFad v4 Proxy