diff --git a/src/ProxyManager/Generator/MethodGenerator.php b/src/ProxyManager/Generator/MethodGenerator.php index bcc9d0b5..1643a50d 100644 --- a/src/ProxyManager/Generator/MethodGenerator.php +++ b/src/ProxyManager/Generator/MethodGenerator.php @@ -6,6 +6,7 @@ use Laminas\Code\Generator\DocBlockGenerator; use Laminas\Code\Generator\MethodGenerator as LaminasMethodGenerator; +use Laminas\Code\Generator\ParameterGenerator; use Laminas\Code\Reflection\MethodReflection; /** @@ -19,7 +20,7 @@ class MethodGenerator extends LaminasMethodGenerator public static function fromReflectionWithoutBodyAndDocBlock(MethodReflection $reflectionMethod): self { /** @var static $method */ - $method = parent::copyMethodSignature($reflectionMethod); + $method = static::copyMethodSignature($reflectionMethod); $method->setInterface(false); $method->setBody(''); @@ -27,6 +28,19 @@ public static function fromReflectionWithoutBodyAndDocBlock(MethodReflection $re return $method; } + public static function copyMethodSignature(MethodReflection $reflectionMethod): parent + { + $method = parent::copyMethodSignature($reflectionMethod); + + foreach ($reflectionMethod->getParameters() as $reflectionParameter) { + $method->setParameter( + ParameterGenerator::fromReflection($reflectionParameter) + ); + } + + return $method; + } + /** * {@inheritDoc} override needed to specify type in more detail */ diff --git a/tests/ProxyManagerTest/ProxyGenerator/ValueHolder/MethodGenerator/ConstructorTest.php b/tests/ProxyManagerTest/ProxyGenerator/ValueHolder/MethodGenerator/ConstructorTest.php index 8ed2d2e5..1065438d 100644 --- a/tests/ProxyManagerTest/ProxyGenerator/ValueHolder/MethodGenerator/ConstructorTest.php +++ b/tests/ProxyManagerTest/ProxyGenerator/ValueHolder/MethodGenerator/ConstructorTest.php @@ -8,6 +8,7 @@ use PHPUnit\Framework\TestCase; use ProxyManager\ProxyGenerator\ValueHolder\MethodGenerator\Constructor; use ProxyManagerTestAsset\ClassWithMixedProperties; +use ProxyManagerTestAsset\ClassWithPromotedProperties; use ProxyManagerTestAsset\ClassWithVariadicConstructorArgument; use ProxyManagerTestAsset\EmptyClass; use ProxyManagerTestAsset\ProxyGenerator\LazyLoading\MethodGenerator\ClassWithTwoPublicProperties; @@ -133,4 +134,23 @@ public function testBodyStructureWithVariadicArguments(): void self::assertSame($expectedCode, $constructor->getBody()); } + + public function testConstructorPropertyPromotion(): void + { + $valueHolder = $this->createMock(PropertyGenerator::class); + + $constructor = Constructor::generateMethod( + new ReflectionClass(ClassWithPromotedProperties::class), + $valueHolder + ); + + self::assertSame('__construct', $constructor->getName()); + $parameters = $constructor->getParameters(); + self::assertCount(2, $parameters); + + // Promoted constructor properties should not be doubled, since they are inherited anyway + $this->assertSame('int $amount', $parameters['amount']->generate()); + $this->assertSame('?int $nullableAmount', $parameters['nullableAmount']->generate()); + } + } diff --git a/tests/ProxyManagerTestAsset/ClassWithPromotedProperties.php b/tests/ProxyManagerTestAsset/ClassWithPromotedProperties.php new file mode 100644 index 00000000..b24fc3f2 --- /dev/null +++ b/tests/ProxyManagerTestAsset/ClassWithPromotedProperties.php @@ -0,0 +1,29 @@ +amount; + } + + public function getNullableAmount(): ?int + { + return $this->nullableAmount; + } +}