diff --git a/src/Symfony/Bundle/FrameworkBundle/Command/ContainerDebugCommand.php b/src/Symfony/Bundle/FrameworkBundle/Command/ContainerDebugCommand.php index 8e8bf8ca3c0ff..f71851a23ace3 100644 --- a/src/Symfony/Bundle/FrameworkBundle/Command/ContainerDebugCommand.php +++ b/src/Symfony/Bundle/FrameworkBundle/Command/ContainerDebugCommand.php @@ -12,6 +12,7 @@ namespace Symfony\Bundle\FrameworkBundle\Command; use Symfony\Bundle\FrameworkBundle\Console\Helper\DescriptorHelper; +use Symfony\Component\Config\ConfigCache; use Symfony\Component\Console\Input\InputArgument; use Symfony\Component\Console\Input\InputOption; use Symfony\Component\Console\Input\InputInterface; @@ -176,19 +177,17 @@ protected function getContainerBuilder() return $this->containerBuilder; } - if (!$this->getApplication()->getKernel()->isDebug()) { - throw new \LogicException('Debug information about the container is only available in debug mode.'); - } + $kernel = $this->getApplication()->getKernel(); - if (!is_file($cachedFile = $this->getContainer()->getParameter('debug.container.dump'))) { - throw new \LogicException('Debug information about the container could not be found. Please clear the cache and try again.'); + if (!$kernel->isDebug() || !(new ConfigCache($kernel->getContainer()->getParameter('debug.container.dump'), true))->isFresh()) { + $buildContainer = \Closure::bind(function () { return $this->buildContainer(); }, $kernel, get_class($kernel)); + $container = $buildContainer(); + $container->getCompilerPassConfig()->setRemovingPasses(array()); + $container->compile(); + } else { + (new XmlFileLoader($container = new ContainerBuilder(), new FileLocator()))->load($kernel->getContainer()->getParameter('debug.container.dump')); } - $container = new ContainerBuilder(); - - $loader = new XmlFileLoader($container, new FileLocator()); - $loader->load($cachedFile); - return $this->containerBuilder = $container; } diff --git a/src/Symfony/Bundle/FrameworkBundle/Console/Descriptor/JsonDescriptor.php b/src/Symfony/Bundle/FrameworkBundle/Console/Descriptor/JsonDescriptor.php index 0b374855a72c5..30410b93ea329 100644 --- a/src/Symfony/Bundle/FrameworkBundle/Console/Descriptor/JsonDescriptor.php +++ b/src/Symfony/Bundle/FrameworkBundle/Console/Descriptor/JsonDescriptor.php @@ -109,7 +109,9 @@ protected function describeContainerServices(ContainerBuilder $builder, array $o $service = $this->resolveServiceDefinition($builder, $serviceId); if ($service instanceof Alias) { - $data['aliases'][$serviceId] = $this->getContainerAliasData($service); + if ($showPrivate || $service->isPublic()) { + $data['aliases'][$serviceId] = $this->getContainerAliasData($service); + } } elseif ($service instanceof Definition) { if (($showPrivate || $service->isPublic())) { $data['definitions'][$serviceId] = $this->getContainerDefinitionData($service, $omitTags, $showArguments); diff --git a/src/Symfony/Bundle/FrameworkBundle/Console/Descriptor/MarkdownDescriptor.php b/src/Symfony/Bundle/FrameworkBundle/Console/Descriptor/MarkdownDescriptor.php index d44d577950729..33cd28d4ce53a 100644 --- a/src/Symfony/Bundle/FrameworkBundle/Console/Descriptor/MarkdownDescriptor.php +++ b/src/Symfony/Bundle/FrameworkBundle/Console/Descriptor/MarkdownDescriptor.php @@ -128,7 +128,6 @@ protected function describeContainerServices(ContainerBuilder $builder, array $o $this->write($title."\n".str_repeat('=', strlen($title))); $serviceIds = isset($options['tag']) && $options['tag'] ? array_keys($builder->findTaggedServiceIds($options['tag'])) : $builder->getServiceIds(); - $showPrivate = isset($options['show_private']) && $options['show_private']; $showArguments = isset($options['show_arguments']) && $options['show_arguments']; $services = array('definitions' => array(), 'aliases' => array(), 'services' => array()); @@ -136,7 +135,9 @@ protected function describeContainerServices(ContainerBuilder $builder, array $o $service = $this->resolveServiceDefinition($builder, $serviceId); if ($service instanceof Alias) { - $services['aliases'][$serviceId] = $service; + if ($showPrivate || $service->isPublic()) { + $services['aliases'][$serviceId] = $service; + } } elseif ($service instanceof Definition) { if (($showPrivate || $service->isPublic())) { $services['definitions'][$serviceId] = $service; diff --git a/src/Symfony/Bundle/FrameworkBundle/Console/Descriptor/TextDescriptor.php b/src/Symfony/Bundle/FrameworkBundle/Console/Descriptor/TextDescriptor.php index 7aae3d3c198bb..fa785d48ed021 100644 --- a/src/Symfony/Bundle/FrameworkBundle/Console/Descriptor/TextDescriptor.php +++ b/src/Symfony/Bundle/FrameworkBundle/Console/Descriptor/TextDescriptor.php @@ -207,6 +207,11 @@ protected function describeContainerServices(ContainerBuilder $builder, array $o } } } + } elseif ($definition instanceof Alias) { + if (!$showPrivate && !$definition->isPublic()) { + unset($serviceIds[$key]); + continue; + } } } diff --git a/src/Symfony/Bundle/FrameworkBundle/Console/Descriptor/XmlDescriptor.php b/src/Symfony/Bundle/FrameworkBundle/Console/Descriptor/XmlDescriptor.php index 461a4e086f9cd..6ed96be1be3d6 100644 --- a/src/Symfony/Bundle/FrameworkBundle/Console/Descriptor/XmlDescriptor.php +++ b/src/Symfony/Bundle/FrameworkBundle/Console/Descriptor/XmlDescriptor.php @@ -320,7 +320,7 @@ private function getContainerServicesDocument(ContainerBuilder $builder, $tag = foreach ($this->sortServiceIds($serviceIds) as $serviceId) { $service = $this->resolveServiceDefinition($builder, $serviceId); - if ($service instanceof Definition && !($showPrivate || $service->isPublic())) { + if (($service instanceof Definition || $service instanceof Alias) && !($showPrivate || $service->isPublic())) { continue; } diff --git a/src/Symfony/Bundle/FrameworkBundle/DependencyInjection/Compiler/ContainerBuilderDebugDumpPass.php b/src/Symfony/Bundle/FrameworkBundle/DependencyInjection/Compiler/ContainerBuilderDebugDumpPass.php index 98fa5c95a15ec..e08fda22134f1 100644 --- a/src/Symfony/Bundle/FrameworkBundle/DependencyInjection/Compiler/ContainerBuilderDebugDumpPass.php +++ b/src/Symfony/Bundle/FrameworkBundle/DependencyInjection/Compiler/ContainerBuilderDebugDumpPass.php @@ -11,11 +11,10 @@ namespace Symfony\Bundle\FrameworkBundle\DependencyInjection\Compiler; +use Symfony\Component\Config\ConfigCache; use Symfony\Component\DependencyInjection\ContainerBuilder; use Symfony\Component\DependencyInjection\Dumper\XmlDumper; use Symfony\Component\DependencyInjection\Compiler\CompilerPassInterface; -use Symfony\Component\Filesystem\Exception\IOException; -use Symfony\Component\Filesystem\Filesystem; /** * Dumps the ContainerBuilder to a cache file so that it can be used by @@ -28,14 +27,9 @@ class ContainerBuilderDebugDumpPass implements CompilerPassInterface { public function process(ContainerBuilder $container) { - $dumper = new XmlDumper($container); - $filename = $container->getParameter('debug.container.dump'); - $filesystem = new Filesystem(); - $filesystem->dumpFile($filename, $dumper->dump(), null); - try { - $filesystem->chmod($filename, 0666, umask()); - } catch (IOException $e) { - // discard chmod failure (some filesystem may not support it) + $cache = new ConfigCache($container->getParameter('debug.container.dump'), true); + if (!$cache->isFresh()) { + $cache->write((new XmlDumper($container))->dump(), $container->getResources()); } } } diff --git a/src/Symfony/Bundle/FrameworkBundle/FrameworkBundle.php b/src/Symfony/Bundle/FrameworkBundle/FrameworkBundle.php index 1794a86f92488..1844f9b4a4391 100644 --- a/src/Symfony/Bundle/FrameworkBundle/FrameworkBundle.php +++ b/src/Symfony/Bundle/FrameworkBundle/FrameworkBundle.php @@ -113,7 +113,7 @@ public function build(ContainerBuilder $container) if ($container->getParameter('kernel.debug')) { $container->addCompilerPass(new AddDebugLogProcessorPass(), PassConfig::TYPE_BEFORE_OPTIMIZATION, -32); $container->addCompilerPass(new UnusedTagsPass(), PassConfig::TYPE_AFTER_REMOVING); - $container->addCompilerPass(new ContainerBuilderDebugDumpPass(), PassConfig::TYPE_AFTER_REMOVING); + $container->addCompilerPass(new ContainerBuilderDebugDumpPass(), PassConfig::TYPE_BEFORE_REMOVING, -255); $this->addCompilerPassIfExists($container, ConfigCachePass::class); $container->addCompilerPass(new CacheCollectorPass()); } diff --git a/src/Symfony/Bundle/FrameworkBundle/Tests/Fixtures/Descriptor/builder_1_arguments.json b/src/Symfony/Bundle/FrameworkBundle/Tests/Fixtures/Descriptor/builder_1_arguments.json index c304b33ac2283..dd3f81f1768e4 100644 --- a/src/Symfony/Bundle/FrameworkBundle/Tests/Fixtures/Descriptor/builder_1_arguments.json +++ b/src/Symfony/Bundle/FrameworkBundle/Tests/Fixtures/Descriptor/builder_1_arguments.json @@ -79,10 +79,6 @@ "alias_1": { "service": "service_1", "public": true - }, - "alias_2": { - "service": "service_2", - "public": false } }, "services": { diff --git a/src/Symfony/Bundle/FrameworkBundle/Tests/Fixtures/Descriptor/builder_1_arguments.md b/src/Symfony/Bundle/FrameworkBundle/Tests/Fixtures/Descriptor/builder_1_arguments.md index 29e34d2b0d94f..757da8278ca34 100644 --- a/src/Symfony/Bundle/FrameworkBundle/Tests/Fixtures/Descriptor/builder_1_arguments.md +++ b/src/Symfony/Bundle/FrameworkBundle/Tests/Fixtures/Descriptor/builder_1_arguments.md @@ -27,11 +27,6 @@ Aliases - Service: `service_1` - Public: yes -### alias_2 - -- Service: `service_2` -- Public: no - Services -------- diff --git a/src/Symfony/Bundle/FrameworkBundle/Tests/Fixtures/Descriptor/builder_1_arguments.txt b/src/Symfony/Bundle/FrameworkBundle/Tests/Fixtures/Descriptor/builder_1_arguments.txt index 0e42596b99233..87f6b2125d764 100644 --- a/src/Symfony/Bundle/FrameworkBundle/Tests/Fixtures/Descriptor/builder_1_arguments.txt +++ b/src/Symfony/Bundle/FrameworkBundle/Tests/Fixtures/Descriptor/builder_1_arguments.txt @@ -6,7 +6,6 @@  Service ID   Class name  ------------------- -------------------------------------------------------- alias_1 alias for "service_1" - alias_2 alias for "service_2" definition_1 Full\Qualified\Class1 service_container Symfony\Component\DependencyInjection\ContainerBuilder ------------------- -------------------------------------------------------- diff --git a/src/Symfony/Bundle/FrameworkBundle/Tests/Fixtures/Descriptor/builder_1_arguments.xml b/src/Symfony/Bundle/FrameworkBundle/Tests/Fixtures/Descriptor/builder_1_arguments.xml index 2d4de06aa84cb..91b292da50248 100644 --- a/src/Symfony/Bundle/FrameworkBundle/Tests/Fixtures/Descriptor/builder_1_arguments.xml +++ b/src/Symfony/Bundle/FrameworkBundle/Tests/Fixtures/Descriptor/builder_1_arguments.xml @@ -1,7 +1,6 @@ - diff --git a/src/Symfony/Bundle/FrameworkBundle/Tests/Fixtures/Descriptor/builder_1_public.json b/src/Symfony/Bundle/FrameworkBundle/Tests/Fixtures/Descriptor/builder_1_public.json index 7f86ccb2ac429..3419083f572bd 100644 --- a/src/Symfony/Bundle/FrameworkBundle/Tests/Fixtures/Descriptor/builder_1_public.json +++ b/src/Symfony/Bundle/FrameworkBundle/Tests/Fixtures/Descriptor/builder_1_public.json @@ -19,10 +19,6 @@ "alias_1": { "service": "service_1", "public": true - }, - "alias_2": { - "service": "service_2", - "public": false } }, "services": { diff --git a/src/Symfony/Bundle/FrameworkBundle/Tests/Fixtures/Descriptor/builder_1_public.md b/src/Symfony/Bundle/FrameworkBundle/Tests/Fixtures/Descriptor/builder_1_public.md index aff2f08191d00..b8c62be4bcf23 100644 --- a/src/Symfony/Bundle/FrameworkBundle/Tests/Fixtures/Descriptor/builder_1_public.md +++ b/src/Symfony/Bundle/FrameworkBundle/Tests/Fixtures/Descriptor/builder_1_public.md @@ -26,11 +26,6 @@ Aliases - Service: `service_1` - Public: yes -### alias_2 - -- Service: `service_2` -- Public: no - Services -------- diff --git a/src/Symfony/Bundle/FrameworkBundle/Tests/Fixtures/Descriptor/builder_1_public.txt b/src/Symfony/Bundle/FrameworkBundle/Tests/Fixtures/Descriptor/builder_1_public.txt index 0e42596b99233..87f6b2125d764 100644 --- a/src/Symfony/Bundle/FrameworkBundle/Tests/Fixtures/Descriptor/builder_1_public.txt +++ b/src/Symfony/Bundle/FrameworkBundle/Tests/Fixtures/Descriptor/builder_1_public.txt @@ -6,7 +6,6 @@  Service ID   Class name  ------------------- -------------------------------------------------------- alias_1 alias for "service_1" - alias_2 alias for "service_2" definition_1 Full\Qualified\Class1 service_container Symfony\Component\DependencyInjection\ContainerBuilder ------------------- -------------------------------------------------------- diff --git a/src/Symfony/Bundle/FrameworkBundle/Tests/Fixtures/Descriptor/builder_1_public.xml b/src/Symfony/Bundle/FrameworkBundle/Tests/Fixtures/Descriptor/builder_1_public.xml index 22a7fb4224127..ac92a28ef6a4d 100644 --- a/src/Symfony/Bundle/FrameworkBundle/Tests/Fixtures/Descriptor/builder_1_public.xml +++ b/src/Symfony/Bundle/FrameworkBundle/Tests/Fixtures/Descriptor/builder_1_public.xml @@ -1,7 +1,6 @@ - diff --git a/src/Symfony/Bundle/FrameworkBundle/Tests/Functional/ContainerDebugCommandTest.php b/src/Symfony/Bundle/FrameworkBundle/Tests/Functional/ContainerDebugCommandTest.php new file mode 100644 index 0000000000000..d19b08f739b82 --- /dev/null +++ b/src/Symfony/Bundle/FrameworkBundle/Tests/Functional/ContainerDebugCommandTest.php @@ -0,0 +1,66 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace Symfony\Bundle\FrameworkBundle\Tests\Functional; + +use Symfony\Bundle\FrameworkBundle\Console\Application; +use Symfony\Component\Console\Tester\ApplicationTester; + +/** + * @group functional + */ +class ContainerDebugCommandTest extends WebTestCase +{ + public function testDumpContainerIfNotExists() + { + static::bootKernel(array('test_case' => 'ContainerDebug', 'root_config' => 'config.yml')); + + $application = new Application(static::$kernel); + $application->setAutoExit(false); + + @unlink(static::$kernel->getContainer()->getParameter('debug.container.dump')); + + $tester = new ApplicationTester($application); + $tester->run(array('command' => 'debug:container')); + + $this->assertFileExists(static::$kernel->getContainer()->getParameter('debug.container.dump')); + } + + public function testNoDebug() + { + static::bootKernel(array('test_case' => 'ContainerDebug', 'root_config' => 'config.yml', 'debug' => false)); + + $application = new Application(static::$kernel); + $application->setAutoExit(false); + + $tester = new ApplicationTester($application); + $tester->run(array('command' => 'debug:container')); + + $this->assertContains('public', $tester->getDisplay()); + } + + public function testPrivateAlias() + { + static::bootKernel(array('test_case' => 'ContainerDebug', 'root_config' => 'config.yml')); + + $application = new Application(static::$kernel); + $application->setAutoExit(false); + + $tester = new ApplicationTester($application); + $tester->run(array('command' => 'debug:container', '--show-private' => true)); + $this->assertContains('public', $tester->getDisplay()); + $this->assertContains('private_alias', $tester->getDisplay()); + + $tester->run(array('command' => 'debug:container')); + $this->assertContains('public', $tester->getDisplay()); + $this->assertNotContains('private_alias', $tester->getDisplay()); + } +} diff --git a/src/Symfony/Bundle/FrameworkBundle/Tests/Functional/app/ContainerDebug/bundles.php b/src/Symfony/Bundle/FrameworkBundle/Tests/Functional/app/ContainerDebug/bundles.php new file mode 100644 index 0000000000000..a73987bcc986a --- /dev/null +++ b/src/Symfony/Bundle/FrameworkBundle/Tests/Functional/app/ContainerDebug/bundles.php @@ -0,0 +1,18 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +use Symfony\Bundle\FrameworkBundle\Tests\Functional\Bundle\TestBundle\TestBundle; +use Symfony\Bundle\FrameworkBundle\FrameworkBundle; + +return array( + new FrameworkBundle(), + new TestBundle(), +); diff --git a/src/Symfony/Bundle/FrameworkBundle/Tests/Functional/app/ContainerDebug/config.yml b/src/Symfony/Bundle/FrameworkBundle/Tests/Functional/app/ContainerDebug/config.yml new file mode 100644 index 0000000000000..f4a5425808440 --- /dev/null +++ b/src/Symfony/Bundle/FrameworkBundle/Tests/Functional/app/ContainerDebug/config.yml @@ -0,0 +1,9 @@ +imports: + - { resource: ../config/default.yml } + +services: + public: + class: Symfony\Bundle\FrameworkBundle\Tests\Fixtures\DeclaredClass + private_alias: + alias: public + public: false