From 203530212af8e9420eb262b9e87fb80565cb4adc Mon Sep 17 00:00:00 2001 From: Nicolas Grekas Date: Thu, 13 May 2021 00:02:37 +0200 Subject: [PATCH] Add AsEntityListener attribute --- Attribute/AsEntityListener.php | 20 +++++++++ DependencyInjection/DoctrineExtension.php | 12 ++++++ .../DoctrineExtensionTest.php | 41 +++++++++++++++++++ .../Fixtures/Php8EntityListener.php | 17 ++++++++ 4 files changed, 90 insertions(+) create mode 100644 Attribute/AsEntityListener.php create mode 100644 Tests/DependencyInjection/Fixtures/Php8EntityListener.php diff --git a/Attribute/AsEntityListener.php b/Attribute/AsEntityListener.php new file mode 100644 index 000000000..aab3af4ba --- /dev/null +++ b/Attribute/AsEntityListener.php @@ -0,0 +1,20 @@ +registerForAutoconfiguration(AbstractIdGenerator::class) ->addTag(IdGeneratorPass::ID_GENERATOR_TAG); + if (method_exists($container, 'registerAttributeForAutoconfiguration')) { + $container->registerAttributeForAutoconfiguration(AsEntityListener::class, static function (ChildDefinition $definition, AsEntityListener $attribute) { + $definition->addTag('doctrine.orm.entity_listener', [ + 'event' => $attribute->event, + 'method' => $attribute->method, + 'lazy' => $attribute->lazy, + 'entity_manager' => $attribute->entityManager, + ]); + }); + } + /** @see DoctrineBundle::boot() */ $container->getDefinition($defaultEntityManagerDefinitionId) ->addTag('container.preload', [ diff --git a/Tests/DependencyInjection/DoctrineExtensionTest.php b/Tests/DependencyInjection/DoctrineExtensionTest.php index 36eff15ab..3396f2018 100644 --- a/Tests/DependencyInjection/DoctrineExtensionTest.php +++ b/Tests/DependencyInjection/DoctrineExtensionTest.php @@ -2,9 +2,12 @@ namespace Doctrine\Bundle\DoctrineBundle\Tests\DependencyInjection; +use Closure; +use Doctrine\Bundle\DoctrineBundle\Attribute\AsEntityListener; use Doctrine\Bundle\DoctrineBundle\CacheWarmer\DoctrineMetadataCacheWarmer; use Doctrine\Bundle\DoctrineBundle\DependencyInjection\DoctrineExtension; use Doctrine\Bundle\DoctrineBundle\Tests\Builder\BundleConfigurationBuilder; +use Doctrine\Bundle\DoctrineBundle\Tests\DependencyInjection\Fixtures\Php8EntityListener; use Doctrine\DBAL\Connection; use Doctrine\DBAL\Driver\Connection as DriverConnection; use Doctrine\DBAL\Sharding\PoolingShardManager; @@ -14,11 +17,13 @@ use InvalidArgumentException; use LogicException; use PHPUnit\Framework\TestCase; +use ReflectionClass; use Symfony\Bridge\Doctrine\Messenger\DoctrineClearEntityManagerWorkerSubscriber; use Symfony\Component\Cache\Adapter\ArrayAdapter; use Symfony\Component\Cache\Adapter\DoctrineAdapter; use Symfony\Component\Cache\Adapter\PhpArrayAdapter; use Symfony\Component\Cache\DoctrineProvider; +use Symfony\Component\DependencyInjection\ChildDefinition; use Symfony\Component\DependencyInjection\Compiler\ResolveChildDefinitionsPass; use Symfony\Component\DependencyInjection\ContainerBuilder; use Symfony\Component\DependencyInjection\Definition; @@ -29,6 +34,7 @@ use function array_values; use function class_exists; use function interface_exists; +use function method_exists; use function sprintf; use function sys_get_temp_dir; @@ -1071,6 +1077,41 @@ public function testShardManager(): void $this->assertEquals($managerClass, $bazManagerDef->getClass()); } + /** @requires PHP 8 */ + public function testAsEntityListenerAttribute() + { + if (! method_exists(ContainerBuilder::class, 'getAutoconfiguredAttributes')) { + $this->markTestSkipped('symfony/dependency-injection 5.3.0 needed'); + } + + $container = $this->getContainer(); + $extension = new DoctrineExtension(); + + $config = BundleConfigurationBuilder::createBuilder() + ->addBaseConnection() + ->addBaseEntityManager() + ->build(); + + $extension->load([$config], $container); + + $attributes = $container->getAutoconfiguredAttributes(); + $this->assertInstanceOf(Closure::class, $attributes[AsEntityListener::class]); + + $reflector = new ReflectionClass(Php8EntityListener::class); + $definition = new ChildDefinition(''); + $attribute = $reflector->getAttributes(AsEntityListener::class)[0]->newInstance(); + + $attributes[AsEntityListener::class]($definition, $attribute); + + $expected = [ + 'event' => null, + 'method' => null, + 'lazy' => null, + 'entity_manager' => null, + ]; + $this->assertSame([$expected], $definition->getTag('doctrine.orm.entity_listener')); + } + /** @param list $bundles */ private function getContainer(array $bundles = ['YamlBundle'], string $vendor = ''): ContainerBuilder { diff --git a/Tests/DependencyInjection/Fixtures/Php8EntityListener.php b/Tests/DependencyInjection/Fixtures/Php8EntityListener.php new file mode 100644 index 000000000..a4c925ca7 --- /dev/null +++ b/Tests/DependencyInjection/Fixtures/Php8EntityListener.php @@ -0,0 +1,17 @@ +