vendor/symfony/src/Symfony/Component/DependencyInjection/Compiler/AnalyzeServiceReferencesPass.php
changeset 0 7f95f8617b0b
equal deleted inserted replaced
-1:000000000000 0:7f95f8617b0b
       
     1 <?php
       
     2 
       
     3 /*
       
     4  * This file is part of the Symfony package.
       
     5  *
       
     6  * (c) Fabien Potencier <fabien@symfony.com>
       
     7  *
       
     8  * For the full copyright and license information, please view the LICENSE
       
     9  * file that was distributed with this source code.
       
    10  */
       
    11 
       
    12 namespace Symfony\Component\DependencyInjection\Compiler;
       
    13 
       
    14 use Symfony\Component\DependencyInjection\Definition;
       
    15 use Symfony\Component\DependencyInjection\Reference;
       
    16 use Symfony\Component\DependencyInjection\ContainerBuilder;
       
    17 
       
    18 /**
       
    19  * Run this pass before passes that need to know more about the relation of
       
    20  * your services.
       
    21  *
       
    22  * This class will populate the ServiceReferenceGraph with information. You can
       
    23  * retrieve the graph in other passes from the compiler.
       
    24  *
       
    25  * @author Johannes M. Schmitt <schmittjoh@gmail.com>
       
    26  */
       
    27 class AnalyzeServiceReferencesPass implements RepeatablePassInterface
       
    28 {
       
    29     private $graph;
       
    30     private $container;
       
    31     private $currentId;
       
    32     private $currentDefinition;
       
    33     private $repeatedPass;
       
    34     private $onlyConstructorArguments;
       
    35 
       
    36     /**
       
    37      * Constructor.
       
    38      *
       
    39      * @param Boolean $onlyConstructorArguments Sets this Service Reference pass to ignore method calls
       
    40      */
       
    41     public function __construct($onlyConstructorArguments = false)
       
    42     {
       
    43         $this->onlyConstructorArguments = (Boolean) $onlyConstructorArguments;
       
    44     }
       
    45 
       
    46     /**
       
    47      * {@inheritDoc}
       
    48      */
       
    49     public function setRepeatedPass(RepeatedPass $repeatedPass) {
       
    50         $this->repeatedPass = $repeatedPass;
       
    51     }
       
    52 
       
    53     /**
       
    54      * Processes a ContainerBuilder object to populate the service reference graph.
       
    55      *
       
    56      * @param ContainerBuilder $container
       
    57      */
       
    58     public function process(ContainerBuilder $container)
       
    59     {
       
    60         $this->container = $container;
       
    61         $this->graph     = $container->getCompiler()->getServiceReferenceGraph();
       
    62         $this->graph->clear();
       
    63 
       
    64         foreach ($container->getDefinitions() as $id => $definition) {
       
    65             if ($definition->isSynthetic() || $definition->isAbstract()) {
       
    66                 continue;
       
    67             }
       
    68 
       
    69             $this->currentId = $id;
       
    70             $this->currentDefinition = $definition;
       
    71             $this->processArguments($definition->getArguments());
       
    72 
       
    73             if (!$this->onlyConstructorArguments) {
       
    74                 $this->processArguments($definition->getMethodCalls());
       
    75                 $this->processArguments($definition->getProperties());
       
    76             }
       
    77         }
       
    78 
       
    79         foreach ($container->getAliases() as $id => $alias) {
       
    80             $this->graph->connect($id, $alias, (string) $alias, $this->getDefinition((string) $alias), null);
       
    81         }
       
    82     }
       
    83 
       
    84     /**
       
    85      * Processes service definitions for arguments to find relationships for the service graph.
       
    86      *
       
    87      * @param array $arguments An array of Reference or Definition objects relating to service definitions
       
    88      */
       
    89     private function processArguments(array $arguments)
       
    90     {
       
    91         foreach ($arguments as $argument) {
       
    92             if (is_array($argument)) {
       
    93                 $this->processArguments($argument);
       
    94             } else if ($argument instanceof Reference) {
       
    95                 $this->graph->connect(
       
    96                     $this->currentId,
       
    97                     $this->currentDefinition,
       
    98                     $this->getDefinitionId((string) $argument),
       
    99                     $this->getDefinition((string) $argument),
       
   100                     $argument
       
   101                 );
       
   102             } else if ($argument instanceof Definition) {
       
   103                 $this->processArguments($argument->getArguments());
       
   104                 $this->processArguments($argument->getMethodCalls());
       
   105                 $this->processArguments($argument->getProperties());
       
   106             }
       
   107         }
       
   108     }
       
   109 
       
   110     /**
       
   111      * Returns a service definition given the full name or an alias.
       
   112      *
       
   113      * @param string $id A full id or alias for a service definition.
       
   114      * @return Definition The definition related to the supplied id
       
   115      */
       
   116     private function getDefinition($id)
       
   117     {
       
   118         $id = $this->getDefinitionId($id);
       
   119 
       
   120         return null === $id ? null : $this->container->getDefinition($id);
       
   121     }
       
   122 
       
   123     private function getDefinitionId($id)
       
   124     {
       
   125         while ($this->container->hasAlias($id)) {
       
   126             $id = (string) $this->container->getAlias($id);
       
   127         }
       
   128 
       
   129         if (!$this->container->hasDefinition($id)) {
       
   130             return null;
       
   131         }
       
   132 
       
   133         return $id;
       
   134     }
       
   135 }