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 9c7e936

Browse files
Merge pull request #44 from enumag/feature/messenger
Add EnvelopeReturnTypeExtension for symfony/messenger
2 parents 649c258 + eb878cf commit 9c7e936

File tree

7 files changed

+110
-14
lines changed

7 files changed

+110
-14
lines changed

‎composer.json‎

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -33,7 +33,8 @@
3333
"phpstan/phpstan-phpunit": "^0.11",
3434
"symfony/framework-bundle": "^3.0 || ^4.0",
3535
"squizlabs/php_codesniffer": "^3.3.2",
36-
"symfony/serializer": "^3|^4"
36+
"symfony/serializer": "^3|^4",
37+
"symfony/messenger": "^4.2"
3738
},
3839
"conflict": {
3940
"symfony/framework-bundle": "<3.0"

‎extension.neon‎

Lines changed: 15 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -12,41 +12,46 @@ services:
1212
class: PHPStan\Symfony\ServiceMapFactory
1313
factory: PHPStan\Symfony\XmlServiceMapFactory(%symfony.container_xml_path%)
1414
-
15-
class: @symfony.serviceMapFactory::create()
15+
factory: @symfony.serviceMapFactory::create()
1616

1717
# ControllerTrait::get()/has() return type
1818
-
19-
class: PHPStan\Type\Symfony\ServiceDynamicReturnTypeExtension(Symfony\Component\DependencyInjection\ContainerInterface, %symfony.constant_hassers%)
19+
factory: PHPStan\Type\Symfony\ServiceDynamicReturnTypeExtension(Symfony\Component\DependencyInjection\ContainerInterface, %symfony.constant_hassers%)
2020
tags: [phpstan.broker.dynamicMethodReturnTypeExtension]
2121
-
22-
class: PHPStan\Type\Symfony\ServiceDynamicReturnTypeExtension(Symfony\Bundle\FrameworkBundle\Controller\Controller, %symfony.constant_hassers%)
22+
factory: PHPStan\Type\Symfony\ServiceDynamicReturnTypeExtension(Symfony\Bundle\FrameworkBundle\Controller\Controller, %symfony.constant_hassers%)
2323
tags: [phpstan.broker.dynamicMethodReturnTypeExtension]
2424
-
25-
class: PHPStan\Type\Symfony\ServiceDynamicReturnTypeExtension(Symfony\Bundle\FrameworkBundle\Controller\AbstractController, %symfony.constant_hassers%)
25+
factory: PHPStan\Type\Symfony\ServiceDynamicReturnTypeExtension(Symfony\Bundle\FrameworkBundle\Controller\AbstractController, %symfony.constant_hassers%)
2626
tags: [phpstan.broker.dynamicMethodReturnTypeExtension]
2727

2828
# ControllerTrait::has() type specification
2929
-
30-
class: PHPStan\Type\Symfony\ServiceTypeSpecifyingExtension(Symfony\Component\DependencyInjection\ContainerInterface)
30+
factory: PHPStan\Type\Symfony\ServiceTypeSpecifyingExtension(Symfony\Component\DependencyInjection\ContainerInterface)
3131
tags: [phpstan.typeSpecifier.methodTypeSpecifyingExtension]
3232
-
33-
class: PHPStan\Type\Symfony\ServiceTypeSpecifyingExtension(Symfony\Bundle\FrameworkBundle\Controller\Controller)
33+
factory: PHPStan\Type\Symfony\ServiceTypeSpecifyingExtension(Symfony\Bundle\FrameworkBundle\Controller\Controller)
3434
tags: [phpstan.typeSpecifier.methodTypeSpecifyingExtension]
3535
-
36-
class: PHPStan\Type\Symfony\ServiceTypeSpecifyingExtension(Symfony\Bundle\FrameworkBundle\Controller\AbstractController)
36+
factory: PHPStan\Type\Symfony\ServiceTypeSpecifyingExtension(Symfony\Bundle\FrameworkBundle\Controller\AbstractController)
3737
tags: [phpstan.typeSpecifier.methodTypeSpecifyingExtension]
3838

3939
# Request::getContent() return type
4040
-
41-
class: PHPStan\Type\Symfony\RequestDynamicReturnTypeExtension
41+
factory: PHPStan\Type\Symfony\RequestDynamicReturnTypeExtension
4242
tags: [phpstan.broker.dynamicMethodReturnTypeExtension]
4343

4444
# HeaderBag::get() return type
4545
-
46-
class: PHPStan\Type\Symfony\HeaderBagDynamicReturnTypeExtension
46+
factory: PHPStan\Type\Symfony\HeaderBagDynamicReturnTypeExtension
4747
tags: [phpstan.broker.dynamicMethodReturnTypeExtension]
4848

4949
# SerializerInterface::deserialize() return type
5050
-
51-
class: PHPStan\Type\Symfony\SerializerInterfaceDynamicReturnTypeExtension
51+
factory: PHPStan\Type\Symfony\SerializerInterfaceDynamicReturnTypeExtension
52+
tags: [phpstan.broker.dynamicMethodReturnTypeExtension]
53+
54+
# Envelope::all() return type
55+
-
56+
factory: PHPStan\Type\Symfony\EnvelopeReturnTypeExtension
5257
tags: [phpstan.broker.dynamicMethodReturnTypeExtension]
Lines changed: 46 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,46 @@
1+
<?php declare(strict_types = 1);
2+
3+
namespace PHPStan\Type\Symfony;
4+
5+
use PhpParser\Node\Expr\MethodCall;
6+
use PHPStan\Analyser\Scope;
7+
use PHPStan\Reflection\MethodReflection;
8+
use PHPStan\Type\ArrayType;
9+
use PHPStan\Type\Constant\ConstantStringType;
10+
use PHPStan\Type\DynamicMethodReturnTypeExtension;
11+
use PHPStan\Type\MixedType;
12+
use PHPStan\Type\ObjectType;
13+
use PHPStan\Type\Type;
14+
15+
final class EnvelopeReturnTypeExtension implements DynamicMethodReturnTypeExtension
16+
{
17+
18+
public function getClass(): string
19+
{
20+
return 'Symfony\Component\Messenger\Envelope';
21+
}
22+
23+
public function isMethodSupported(MethodReflection $methodReflection): bool
24+
{
25+
return $methodReflection->getName() === 'all';
26+
}
27+
28+
public function getTypeFromMethodCall(
29+
MethodReflection $methodReflection,
30+
MethodCall $methodCall,
31+
Scope $scope
32+
): Type
33+
{
34+
if (count($methodCall->args) === 0) {
35+
return new ArrayType(new MixedType(), new ArrayType(new MixedType(), new ObjectType('Symfony\Component\Messenger\Stamp\StampInterface')));
36+
}
37+
38+
$argType = $scope->getType($methodCall->args[0]->value);
39+
if (!$argType instanceof ConstantStringType) {
40+
return new ArrayType(new MixedType(), new ObjectType('Symfony\Component\Messenger\Stamp\StampInterface'));
41+
}
42+
43+
return new ArrayType(new MixedType(), new ObjectType($argType->getValue()));
44+
}
45+
46+
}

‎tests/Symfony/NeonTest.php‎

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -40,7 +40,7 @@ public function testExtensionNeon(): void
4040
], $container->getParameters());
4141

4242
self::assertCount(2, $container->findByTag('phpstan.rules.rule'));
43-
self::assertCount(6, $container->findByTag('phpstan.broker.dynamicMethodReturnTypeExtension'));
43+
self::assertCount(7, $container->findByTag('phpstan.broker.dynamicMethodReturnTypeExtension'));
4444
self::assertCount(3, $container->findByTag('phpstan.typeSpecifier.methodTypeSpecifyingExtension'));
4545
self::assertInstanceOf(ServiceMap::class, $container->getByType(ServiceMap::class));
4646
}
Lines changed: 32 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,32 @@
1+
<?php declare(strict_types = 1);
2+
3+
namespace PHPStan\Type\Symfony;
4+
5+
use Iterator;
6+
use Symfony\Component\Messenger\Stamp\ReceivedStamp;
7+
use Symfony\Component\Messenger\Stamp\StampInterface;
8+
9+
final class EnvelopeReturnTypeExtensionTest extends ExtensionTestCase
10+
{
11+
12+
/**
13+
* @dataProvider getProvider
14+
*/
15+
public function testAll(string $expression, string $type): void
16+
{
17+
$this->processFile(
18+
__DIR__ . '/envelope_all.php',
19+
$expression,
20+
$type,
21+
new EnvelopeReturnTypeExtension()
22+
);
23+
}
24+
25+
public function getProvider(): Iterator
26+
{
27+
yield ['$test1', 'array<' . ReceivedStamp::class . '>'];
28+
yield ['$test2', 'array<' . StampInterface::class . '>'];
29+
yield ['$test3', 'array<array<' . StampInterface::class . '>>'];
30+
}
31+
32+
}

‎tests/Type/Symfony/ExtensionTestCase.php‎

Lines changed: 5 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -10,7 +10,7 @@
1010
use PHPStan\Broker\AnonymousClassNameHelper;
1111
use PHPStan\Cache\Cache;
1212
use PHPStan\File\FileHelper;
13-
use PHPStan\Node\InClassMethodNode;
13+
use PHPStan\Node\VirtualNode;
1414
use PHPStan\PhpDoc\PhpDocStringResolver;
1515
use PHPStan\PhpDoc\TypeNodeResolver;
1616
use PHPStan\Testing\TestCase;
@@ -61,7 +61,10 @@ protected function processFile(
6161
$parser->parseFile($file),
6262
$this->createScopeFactory($broker, $typeSpecifier)->create(ScopeContext::create($file)),
6363
function (Node $node, Scope $scope) use ($expression, $type, &$run): void {
64-
if ((new Standard())->prettyPrint([$node instanceof InClassMethodNode ? $node->getOriginalNode() : $node]) !== 'die') {
64+
if ($node instanceof VirtualNode) {
65+
return;
66+
}
67+
if ((new Standard())->prettyPrint([$node]) !== 'die') {
6568
return;
6669
}
6770
/** @var \PhpParser\Node\Stmt\Expression $expNode */

‎tests/Type/Symfony/envelope_all.php‎

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,9 @@
1+
<?php declare(strict_types = 1);
2+
3+
$envelope = new \Symfony\Component\Messenger\Envelope(new stdClass());
4+
5+
$test1 = $envelope->all(\Symfony\Component\Messenger\Stamp\ReceivedStamp::class);
6+
$test2 = $envelope->all(random_bytes(1));
7+
$test3 = $envelope->all();
8+
9+
die;

0 commit comments

Comments
(0)

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