diff -r 000000000000 -r 7f95f8617b0b vendor/symfony/src/Symfony/Component/DependencyInjection/Compiler/ResolveInvalidReferencesPass.php --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/vendor/symfony/src/Symfony/Component/DependencyInjection/Compiler/ResolveInvalidReferencesPass.php Sat Sep 24 15:40:41 2011 +0200 @@ -0,0 +1,102 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace Symfony\Component\DependencyInjection\Compiler; + +use Symfony\Component\DependencyInjection\ContainerInterface; +use Symfony\Component\DependencyInjection\Reference; +use Symfony\Component\DependencyInjection\ContainerBuilder; + +/** + * Emulates the invalid behavior if the reference is not found within the + * container. + * + * @author Johannes M. Schmitt + */ +class ResolveInvalidReferencesPass implements CompilerPassInterface +{ + private $container; + + /** + * Process the ContainerBuilder to resolve invalid references. + * + * @param ContainerBuilder $container + */ + public function process(ContainerBuilder $container) + { + $this->container = $container; + foreach ($container->getDefinitions() as $definition) { + if ($definition->isSynthetic() || $definition->isAbstract()) { + continue; + } + + $definition->setArguments( + $this->processArguments($definition->getArguments()) + ); + + $calls = array(); + foreach ($definition->getMethodCalls() as $call) { + try { + $calls[] = array($call[0], $this->processArguments($call[1], true)); + } catch (\RuntimeException $ignore) { + // this call is simply removed + } + } + $definition->setMethodCalls($calls); + + $properties = array(); + foreach ($definition->getProperties() as $name => $value) { + try { + $value = $this->processArguments(array($value), true); + $properties[$name] = reset($value); + } catch (\RuntimeException $ignore) { + // ignore property + } + } + $definition->setProperties($properties); + } + } + + /** + * Processes arguments to determine invalid references. + * + * @param array $arguments An array of Reference objects + * @param Boolean $inMethodCall + */ + private function processArguments(array $arguments, $inMethodCall = false) + { + foreach ($arguments as $k => $argument) { + if (is_array($argument)) { + $arguments[$k] = $this->processArguments($argument, $inMethodCall); + } else if ($argument instanceof Reference) { + $id = (string) $argument; + + $invalidBehavior = $argument->getInvalidBehavior(); + $exists = $this->container->has($id); + + // resolve invalid behavior + if ($exists && ContainerInterface::EXCEPTION_ON_INVALID_REFERENCE !== $invalidBehavior) { + $arguments[$k] = new Reference($id); + } else if (!$exists && ContainerInterface::NULL_ON_INVALID_REFERENCE === $invalidBehavior) { + $arguments[$k] = null; + } else if (!$exists && ContainerInterface::IGNORE_ON_INVALID_REFERENCE === $invalidBehavior) { + if ($inMethodCall) { + throw new \RuntimeException('Method shouldn\'t be called.'); + } + + $arguments[$k] = null; + } + } + } + + return $arguments; + } +}