Skip to content

Navigation Menu

Sign in
Appearance settings

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Sign up
Appearance settings

Commit 6ff8fc0

Browse files
Move determining the union and intersection with new lines to a proper place and handle them
1 parent 122bb31 commit 6ff8fc0

File tree

3 files changed

+97
-61
lines changed

3 files changed

+97
-61
lines changed

‎src/Parser/TokenIterator.php

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -208,6 +208,14 @@ public function tryConsumeTokenType(int $tokenType): bool
208208
/** @phpstan-impure */
209209
public function skipNewLineTokens(): void
210210
{
211+
if (!$this->isCurrentTokenType(Lexer::TOKEN_PHPDOC_EOL)) {
212+
return;
213+
}
214+
215+
if ($this->newline === null) {
216+
$this->detectNewline();
217+
}
218+
211219
do {
212220
$foundNewLine = $this->tryConsumeTokenType(Lexer::TOKEN_PHPDOC_EOL);
213221
} while ($foundNewLine === true);

‎src/Parser/TypeParser.php

Lines changed: 31 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -40,17 +40,44 @@ public function parse(TokenIterator $tokens): Ast\Type\TypeNode
4040
} else {
4141
$type = $this->parseAtomic($tokens);
4242

43-
if ($tokens->isCurrentTokenType(Lexer::TOKEN_UNION)) {
44-
$type = $this->parseUnion($tokens, $type);
43+
$tokens->pushSavePoint();
44+
$tokens->skipNewLineTokens();
45+
46+
try {
47+
$enrichedType = $this->enrichTypeOnUnionOrIntersection($tokens, $type);
48+
49+
} catch (ParserException $parserException) {
50+
$enrichedType = null;
51+
}
52+
53+
if ($enrichedType !== null) {
54+
$type = $enrichedType;
55+
$tokens->dropSavePoint();
4556

46-
} elseif ($tokens->isCurrentTokenType(Lexer::TOKEN_INTERSECTION)) {
47-
$type = $this->parseIntersection($tokens, $type);
57+
} else {
58+
$tokens->rollback();
59+
$type = $this->enrichTypeOnUnionOrIntersection($tokens, $type) ?? $type;
4860
}
4961
}
5062

5163
return $this->enrichWithAttributes($tokens, $type, $startLine, $startIndex);
5264
}
5365

66+
/** @phpstan-impure */
67+
private function enrichTypeOnUnionOrIntersection(TokenIterator $tokens, Ast\Type\TypeNode $type): ?Ast\Type\TypeNode
68+
{
69+
if ($tokens->isCurrentTokenType(Lexer::TOKEN_UNION)) {
70+
return $this->parseUnion($tokens, $type);
71+
72+
}
73+
74+
if ($tokens->isCurrentTokenType(Lexer::TOKEN_INTERSECTION)) {
75+
return $this->parseIntersection($tokens, $type);
76+
}
77+
78+
return null;
79+
}
80+
5481
/**
5582
* @internal
5683
* @template T of Ast\Node
@@ -412,8 +439,6 @@ public function parseGeneric(TokenIterator $tokens, Ast\Type\IdentifierTypeNode
412439
while (
413440
$isFirst
414441
|| $tokens->tryConsumeTokenType(Lexer::TOKEN_COMMA)
415-
|| $tokens->tryConsumeTokenType(Lexer::TOKEN_UNION)
416-
|| $tokens->tryConsumeTokenType(Lexer::TOKEN_INTERSECTION)
417442
) {
418443
$tokens->skipNewLineTokens();
419444

‎tests/PHPStan/Parser/PhpDocParserTest.php

Lines changed: 58 additions & 55 deletions
Original file line numberDiff line numberDiff line change
@@ -4053,20 +4053,21 @@ public function provideMultiLinePhpDocData(): iterable
40534053
new IdentifierTypeNode('array'),
40544054
[
40554055
new IdentifierTypeNode('string'),
4056-
ArrayShapeNode::createSealed([
4057-
new ArrayShapeItemNode(new IdentifierTypeNode('foo1'), false, new IdentifierTypeNode('int')),
4058-
new ArrayShapeItemNode(new IdentifierTypeNode('bar1'), true, new IdentifierTypeNode('true')),
4059-
]),
4060-
ArrayShapeNode::createSealed([
4061-
new ArrayShapeItemNode(new IdentifierTypeNode('foo1'), false, new IdentifierTypeNode('int')),
4062-
new ArrayShapeItemNode(new IdentifierTypeNode('foo2'), false, new IdentifierTypeNode('true')),
4063-
new ArrayShapeItemNode(new IdentifierTypeNode('bar1'), true, new IdentifierTypeNode('true')),
4056+
new UnionTypeNode([
4057+
ArrayShapeNode::createSealed([
4058+
new ArrayShapeItemNode(new IdentifierTypeNode('foo1'), false, new IdentifierTypeNode('int')),
4059+
new ArrayShapeItemNode(new IdentifierTypeNode('bar1'), true, new IdentifierTypeNode('true')),
4060+
]),
4061+
ArrayShapeNode::createSealed([
4062+
new ArrayShapeItemNode(new IdentifierTypeNode('foo1'), false, new IdentifierTypeNode('int')),
4063+
new ArrayShapeItemNode(new IdentifierTypeNode('foo2'), false, new IdentifierTypeNode('true')),
4064+
new ArrayShapeItemNode(new IdentifierTypeNode('bar1'), true, new IdentifierTypeNode('true')),
4065+
]),
40644066
]),
40654067
],
40664068
[
40674069
GenericTypeNode::VARIANCE_INVARIANT,
40684070
GenericTypeNode::VARIANCE_INVARIANT,
4069-
GenericTypeNode::VARIANCE_INVARIANT,
40704071
],
40714072
)),
40724073
]),
@@ -4111,20 +4112,21 @@ public function provideMultiLinePhpDocData(): iterable
41114112
new IdentifierTypeNode('array'),
41124113
[
41134114
new IdentifierTypeNode('string'),
4114-
ArrayShapeNode::createSealed([
4115-
new ArrayShapeItemNode(new IdentifierTypeNode('foo1'), false, new IdentifierTypeNode('int')),
4116-
new ArrayShapeItemNode(new IdentifierTypeNode('bar1'), true, new IdentifierTypeNode('true')),
4117-
]),
4118-
ArrayShapeNode::createSealed([
4119-
new ArrayShapeItemNode(new IdentifierTypeNode('foo1'), false, new IdentifierTypeNode('int')),
4120-
new ArrayShapeItemNode(new IdentifierTypeNode('foo2'), false, new IdentifierTypeNode('true')),
4121-
new ArrayShapeItemNode(new IdentifierTypeNode('bar1'), true, new IdentifierTypeNode('true')),
4115+
new UnionTypeNode([
4116+
ArrayShapeNode::createSealed([
4117+
new ArrayShapeItemNode(new IdentifierTypeNode('foo1'), false, new IdentifierTypeNode('int')),
4118+
new ArrayShapeItemNode(new IdentifierTypeNode('bar1'), true, new IdentifierTypeNode('true')),
4119+
]),
4120+
ArrayShapeNode::createSealed([
4121+
new ArrayShapeItemNode(new IdentifierTypeNode('foo1'), false, new IdentifierTypeNode('int')),
4122+
new ArrayShapeItemNode(new IdentifierTypeNode('foo2'), false, new IdentifierTypeNode('true')),
4123+
new ArrayShapeItemNode(new IdentifierTypeNode('bar1'), true, new IdentifierTypeNode('true')),
4124+
]),
41224125
]),
41234126
],
41244127
[
41254128
GenericTypeNode::VARIANCE_INVARIANT,
41264129
GenericTypeNode::VARIANCE_INVARIANT,
4127-
GenericTypeNode::VARIANCE_INVARIANT,
41284130
],
41294131
)),
41304132
]),
@@ -4159,49 +4161,50 @@ public function provideMultiLinePhpDocData(): iterable
41594161
[
41604162
new IdentifierTypeNode('string'),
41614163
new UnionTypeNode([
4162-
new GenericTypeNode(
4163-
new IdentifierTypeNode('class-string'),
4164-
[new IdentifierTypeNode('Factory\\FactoryInterface')],
4165-
[GenericTypeNode::VARIANCE_INVARIANT],
4166-
),
4167-
new IdentifierTypeNode('Factory\\FactoryInterface'),
4168-
]),
4169-
new CallableTypeNode(
4170-
new IdentifierTypeNode('callable'),
4171-
[
4172-
new CallableTypeParameterNode(new IdentifierTypeNode('ContainerInterface'), false, false, '', false),
4173-
new CallableTypeParameterNode(
4174-
new NullableTypeNode(
4175-
new IdentifierTypeNode('string'),
4176-
),
4177-
false,
4178-
false,
4179-
'',
4180-
false,
4164+
new UnionTypeNode([
4165+
new GenericTypeNode(
4166+
new IdentifierTypeNode('class-string'),
4167+
[new IdentifierTypeNode('Factory\\FactoryInterface')],
4168+
[GenericTypeNode::VARIANCE_INVARIANT],
41814169
),
4182-
new CallableTypeParameterNode(
4183-
new UnionTypeNode([
4184-
new GenericTypeNode(
4185-
new IdentifierTypeNode('array'),
4186-
[new IdentifierTypeNode('mixed')],
4187-
[GenericTypeNode::VARIANCE_INVARIANT],
4170+
new IdentifierTypeNode('Factory\\FactoryInterface'),
4171+
]),
4172+
new CallableTypeNode(
4173+
new IdentifierTypeNode('callable'),
4174+
[
4175+
new CallableTypeParameterNode(new IdentifierTypeNode('ContainerInterface'), false, false, '', false),
4176+
new CallableTypeParameterNode(
4177+
new NullableTypeNode(
4178+
new IdentifierTypeNode('string'),
41884179
),
4189-
new IdentifierTypeNode('null'),
4190-
]),
4191-
false,
4192-
false,
4193-
'',
4194-
false,
4195-
),
4196-
],
4197-
new IdentifierTypeNode('object'),
4198-
[],
4199-
),
4180+
false,
4181+
false,
4182+
'',
4183+
false,
4184+
),
4185+
new CallableTypeParameterNode(
4186+
new UnionTypeNode([
4187+
new GenericTypeNode(
4188+
new IdentifierTypeNode('array'),
4189+
[new IdentifierTypeNode('mixed')],
4190+
[GenericTypeNode::VARIANCE_INVARIANT],
4191+
),
4192+
new IdentifierTypeNode('null'),
4193+
]),
4194+
false,
4195+
false,
4196+
'',
4197+
false,
4198+
),
4199+
],
4200+
new IdentifierTypeNode('object'),
4201+
[],
4202+
),
4203+
]),
42004204
],
42014205
[
42024206
GenericTypeNode::VARIANCE_INVARIANT,
42034207
GenericTypeNode::VARIANCE_INVARIANT,
4204-
GenericTypeNode::VARIANCE_INVARIANT,
42054208
],
42064209
),
42074210
)),

0 commit comments

Comments
(0)

AltStyle によって変換されたページ (->オリジナル) /