Skip to content

Commit cea6eb0

Browse files
author
Bartłomiej Nowak
committed
implementation for interfaces
1 parent 08d6b9b commit cea6eb0

File tree

3 files changed

+43
-10
lines changed

3 files changed

+43
-10
lines changed

extension.neon

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -13,9 +13,10 @@ parameters:
1313
consoleApplicationLoader: null
1414
messenger:
1515
handleTraitWrappers:
16-
# move that params to tests only
16+
# todo move that params to tests only
1717
- MessengerHandleTrait\QueryBus::dispatch
18-
- MessengerHandleTrait\QueryBus2::dispatch
18+
- MessengerHandleTrait\QueryBus::dispatch2
19+
- MessengerHandleTrait\QueryBusInterface::dispatch
1920
featureToggles:
2021
skipCheckGenericClasses:
2122
- Symfony\Component\Form\AbstractType

src/Type/Symfony/MessengerHandleTraitWrapperReturnTypeExtension.php

Lines changed: 24 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,7 @@
66
use PhpParser\Node\Expr\MethodCall;
77
use PhpParser\Node\Identifier;
88
use PHPStan\Analyser\Scope;
9+
use PHPStan\Reflection\ReflectionProvider;
910
use PHPStan\Symfony\Configuration;
1011
use PHPStan\Symfony\MessageMap;
1112
use PHPStan\Symfony\MessageMapFactory;
@@ -19,7 +20,7 @@
1920
* Configurable extension for resolving return types of methods that internally use HandleTrait.
2021
*
2122
* Configured via PHPStan parameters under symfony.messenger.handleTraitWrappers with
22-
* "Class::method" patterns, e.g.:
23+
* "class::method" patterns, e.g.:
2324
* - App\Bus\QueryBus::dispatch
2425
* - App\Bus\QueryBus::query
2526
* - App\Bus\CommandBus::execute
@@ -37,10 +38,14 @@ final class MessengerHandleTraitWrapperReturnTypeExtension implements Expression
3738
/** @var array<string> */
3839
private $wrappers;
3940

40-
public function __construct(MessageMapFactory $messageMapFactory, Configuration $configuration)
41+
/** @var ReflectionProvider */
42+
private $reflectionProvider;
43+
44+
public function __construct(MessageMapFactory $messageMapFactory, Configuration $configuration, ReflectionProvider $reflectionProvider)
4145
{
4246
$this->messageMapFactory = $messageMapFactory;
4347
$this->wrappers = $configuration->getMessengerHandleTraitWrappers();
48+
$this->reflectionProvider = $reflectionProvider;
4449
}
4550

4651
public function getType(Expr $expr, Scope $scope): ?Type
@@ -89,8 +94,23 @@ private function isSupported(Expr $expr, Scope $scope): bool
8994
$className = $classNames[0];
9095
$classMethodCombination = $className . '::' . $methodName;
9196

92-
// Check if this class::method combination is configured
93-
return in_array($classMethodCombination, $this->wrappers, true);
97+
// Check if this exact class::method combination is configured
98+
if (in_array($classMethodCombination, $this->wrappers, true)) {
99+
return true;
100+
}
101+
102+
// Check if any interface implemented by this class::method is configured
103+
if ($this->reflectionProvider->hasClass($className)) {
104+
$classReflection = $this->reflectionProvider->getClass($className);
105+
foreach ($classReflection->getInterfaces() as $interface) {
106+
$interfaceMethodCombination = $interface->getName() . '::' . $methodName;
107+
if (in_array($interfaceMethodCombination, $this->wrappers, true)) {
108+
return true;
109+
}
110+
}
111+
}
112+
113+
return false;
94114
}
95115

96116
private function getMessageMap(): MessageMap

tests/Type/Symfony/data/messenger_handle_trait.php

Lines changed: 16 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -62,9 +62,18 @@ public function dispatch(object $query): mixed
6262
{
6363
return $this->handle($query);
6464
}
65+
66+
public function dispatch2(object $query): mixed
67+
{
68+
return $this->handle($query);
69+
}
70+
}
71+
72+
interface QueryBusInterface {
73+
public function dispatch(object $query): mixed;
6574
}
6675

67-
class QueryBus2 {
76+
class QueryBusWithInterface implements QueryBusInterface {
6877
use HandleTrait;
6978

7079
public function dispatch(object $query): mixed
@@ -87,11 +96,14 @@ public function action()
8796

8897
assertType(TaggedResult::class, $queryBus->dispatch(new TaggedQuery()));
8998

99+
assertType(RegularQueryResult::class, $queryBus->dispatch2(new RegularQuery()));
100+
101+
$queryBusWithInterface = new QueryBusWithInterface();
102+
103+
assertType(RegularQueryResult::class, $queryBusWithInterface->dispatch(new RegularQuery()));
104+
90105
// HandleTrait will throw exception in fact due to multiple handle methods/handlers per single query
91106
assertType('mixed', $queryBus->dispatch(new MultiHandlesForInTheSameHandlerQuery()));
92107
assertType('mixed', $queryBus->dispatch(new MultiHandlersForTheSameMessageQuery()));
93-
94-
$queryBus2 = new QueryBus2();
95-
assertType(TaggedResult::class, $queryBus2->dispatch(new TaggedQuery()));
96108
}
97109
}

0 commit comments

Comments
 (0)