Browse Source

Merge pull request #1243 from tyx/dev/extension-multiple-target

Allow to add extensions on multiple target
Thomas 11 years ago
parent
commit
33248c0954

+ 32 - 24
DependencyInjection/Compiler/ExtensionCompilerPass.php

@@ -27,23 +27,28 @@ class ExtensionCompilerPass implements CompilerPassInterface
     public function process(ContainerBuilder $container)
     {
         $universalExtensions = array();
-        foreach ($container->findTaggedServiceIds('sonata.admin.extension') as $id => $attributes) {
 
-            $target = false;
-            if (isset($attributes[0]['target'])) {
-                $target = $attributes[0]['target'];
-            }
+        foreach ($container->findTaggedServiceIds('sonata.admin.extension') as $id => $tags) {
+            foreach ($tags as $attributes) {
+                $target = false;
 
-            if (isset($attributes[0]['global']) && $attributes[0]['global']) {
-                $universalExtensions[] = $id;
-            }
+                if (isset($attributes['target'])) {
+                    $target = $attributes['target'];
+                }
 
-            if (!$target || !$container->hasDefinition($target)) {
-                continue;
-            }
+                if (isset($attributes['global']) && $attributes['global']) {
+                    $universalExtensions[] = $id;
+                }
 
-            $container->getDefinition($target)
-                ->addMethodCall('addExtension', array(new Reference($id)));
+                if (!$target || !$container->hasDefinition($target)) {
+                    continue;
+                }
+
+                $container
+                    ->getDefinition($target)
+                    ->addMethodCall('addExtension', array(new Reference($id)))
+                ;
+            }
         }
 
         $extensionConfig = $container->getParameter('sonata.admin.extension.map');
@@ -57,8 +62,9 @@ class ExtensionCompilerPass implements CompilerPassInterface
             }
 
             $extensions = $this->getExtensionsForAdmin($id, $admin, $container, $extensionMap);
+
             foreach ($extensions as $extension) {
-                if(!$container->hasDefinition($extension)){
+                if (!$container->hasDefinition($extension)) {
                     throw new \InvalidArgumentException(sprintf('Unable to find extension service for id %s', $extension));
                 }
                 $admin->addMethodCall('addExtension', array(new Reference($extension)));
@@ -84,8 +90,8 @@ class ExtensionCompilerPass implements CompilerPassInterface
         foreach ($extensionMap as $type => $subjects) {
             foreach ($subjects as $subject => $extensionList) {
 
-                if('admins' == $type){
-                    if($id == $subject){
+                if ('admins' == $type) {
+                    if ($id == $subject) {
                         $extensions = array_merge($extensions, $extensionList);
                     }
                 } else {
@@ -94,29 +100,30 @@ class ExtensionCompilerPass implements CompilerPassInterface
                     $subjectReflection = new \ReflectionClass($subject);
                 }
 
-                if('instanceof' == $type){
-                    if($subjectReflection->getName() == $classReflection->getName() || $classReflection->isSubclassOf($subject)){
+                if ('instanceof' == $type) {
+                    if ($subjectReflection->getName() == $classReflection->getName() || $classReflection->isSubclassOf($subject)) {
                         $extensions = array_merge($extensions, $extensionList);
                     }
                 }
 
-                if('implements' == $type){
-                    if($classReflection->implementsInterface($subject)){
+                if ('implements' == $type) {
+                    if ($classReflection->implementsInterface($subject)) {
                         $extensions = array_merge($extensions, $extensionList);
                     }
                 }
 
-                if('extends' == $type){
-                    if($classReflection->isSubclassOf($subject)){
+                if ('extends' == $type) {
+                    if ($classReflection->isSubclassOf($subject)) {
                         $extensions = array_merge($extensions, $extensionList);
                     }
                 }
             }
         }
 
-        if(isset($excludes[$id])){
+        if (isset($excludes[$id])) {
             $extensions = array_diff($extensions, $excludes[$id]);
         }
+
         return $extensions;
     }
 
@@ -149,13 +156,14 @@ class ExtensionCompilerPass implements CompilerPassInterface
         foreach ($config as $extension => $options) {
             foreach ($options as $key => $value) {
                 foreach ($value as $source) {
-                    if(!isset($extensionMap[$key][$source])){
+                    if (!isset($extensionMap[$key][$source])) {
                         $extensionMap[$key][$source] = array();
                     }
                     array_push($extensionMap[$key][$source], $extension);
                 }
             }
         }
+
         return $extensionMap;
     }
 }

+ 2 - 1
Resources/doc/reference/extensions.rst

@@ -30,7 +30,7 @@ Configuration
 There are two ways to configure your extensions and connect them to an admin.
 
 You can include this information in the service definition of your extension.
-Add the tag *sonata.admin.extension* and use the *target* attribute to point to the admin you want to modify.
+Add the tag *sonata.admin.extension* and use the *target* attribute to point to the admin you want to modify. Please note you can specify as many tags you want.
 Set the *global* attribute to *true* and the extension will be added to all admins.
 
 .. configuration-block::
@@ -42,6 +42,7 @@ Set the *global* attribute to *true* and the extension will be added to all admi
                 class: Acme\Demo\BlogBundle\Admin\Extension\PublishStatusAdminExtension
                 tags:
                     - { name: sonata.admin.extension, target: acme.demo.admin.article }
+                    - { name: sonata.admin.extension, target: acme.demo.admin.blog }
 
             acme.demo.order.extension:
                 class: Acme\Demo\BlogBundle\Admin\Extension\OrderAdminExtension

+ 4 - 2
Tests/DependencyInjection/Compiler/ExtensionCompilerPassTest.php

@@ -236,10 +236,11 @@ class ExtensionCompilerPassTest extends \PHPUnit_Framework_TestCase
 
         $def = $container->get('sonata_article_admin');
         $extensions = $def->getExtensions();
-        $this->assertCount(3, $extensions);
+        $this->assertCount(4, $extensions);
         $this->assertInstanceOf(get_class($this->securityExtension), $extensions[0]);
         $this->assertInstanceOf(get_class($this->publishExtension), $extensions[1]);
         $this->assertInstanceOf(get_class($this->orderExtension), $extensions[2]);
+        $this->assertInstanceOf(get_class($this->filterExtension), $extensions[3]);
 
         $def = $container->get('sonata_news_admin');
         $extensions = $def->getExtensions();
@@ -343,7 +344,8 @@ class ExtensionCompilerPassTest extends \PHPUnit_Framework_TestCase
         $container
             ->register('sonata_extension_filter')
             ->setClass(get_class($this->filterExtension))
-            ->addTag('sonata.admin.extension', array('target' => 'sonata_news_admin'));
+            ->addTag('sonata.admin.extension', array('target' => 'sonata_news_admin'))
+            ->addTag('sonata.admin.extension', array('target' => 'sonata_article_admin'));
 
         return $container;
     }