Skip to content

Commit

Permalink
feature #26921 [DI][FrameworkBundle] Hide service ids that start with…
Browse files Browse the repository at this point in the history
… a dot (nicolas-grekas)

This PR was merged into the 4.1-dev branch.

Discussion
----------

[DI][FrameworkBundle] Hide service ids that start with a dot

| Q             | A
| ------------- | ---
| Branch?       | master
| Bug fix?      | no
| New feature?  | yes
| BC breaks?    | no
| Deprecations? | yes
| Tests pass?   | yes
| Fixed tickets | #26630
| License       | MIT
| Doc PR        | -

Now that services are private by default, `debug:container` should display them by default.
In fact, the public/private concept should not trigger a difference in visibility for this command.

Instead, I propose to handle service ids that start with a dot as hidden services.

PR should be ready.

(For reference, I tried using a tag instead in #26891, but that doesn't work in practice when working on the implementation.)

Commits
-------

cea051e [DI][FrameworkBundle] Hide service ids that start with a dot
  • Loading branch information
fabpot committed Apr 20, 2018
2 parents 1b1c03a + cea051e commit 833909b
Show file tree
Hide file tree
Showing 58 changed files with 267 additions and 264 deletions.
Expand Up @@ -48,8 +48,9 @@ protected function configure()
$this
->setDefinition(array(
new InputArgument('name', InputArgument::OPTIONAL, 'A service name (foo)'),
new InputOption('show-private', null, InputOption::VALUE_NONE, 'Used to show public *and* private services'),
new InputOption('show-private', null, InputOption::VALUE_NONE, 'Used to show public *and* private services (deprecated)'),
new InputOption('show-arguments', null, InputOption::VALUE_NONE, 'Used to show arguments in services'),
new InputOption('show-hidden', null, InputOption::VALUE_NONE, 'Used to show hidden (internal) services'),
new InputOption('tag', null, InputOption::VALUE_REQUIRED, 'Shows all services with a specific tag'),
new InputOption('tags', null, InputOption::VALUE_NONE, 'Displays tagged services for an application'),
new InputOption('parameter', null, InputOption::VALUE_REQUIRED, 'Displays a specific parameter for an application'),
Expand All @@ -72,11 +73,6 @@ protected function configure()
<info>php %command.full_name% --types</info>
By default, private services are hidden. You can display all services by
using the <info>--show-private</info> flag:
<info>php %command.full_name% --show-private</info>
Use the --tags option to display tagged <comment>public</comment> services grouped by tag:
<info>php %command.full_name% --tags</info>
Expand All @@ -93,6 +89,11 @@ protected function configure()
<info>php %command.full_name% --parameter=kernel.debug</info>
By default, internal services are hidden. You can display them
using the <info>--show-hidden</info> flag:
<info>php %command.full_name% --show-hidden</info>
EOF
)
;
Expand All @@ -103,14 +104,18 @@ protected function configure()
*/
protected function execute(InputInterface $input, OutputInterface $output)
{
if ($input->getOption('show-private')) {
@trigger_error('The "--show-private" option no longer has any effect and is deprecated since Symfony 4.1.', E_USER_DEPRECATED);
}

$io = new SymfonyStyle($input, $output);
$errorIo = $io->getErrorStyle();

$this->validateInput($input);
$object = $this->getContainerBuilder();

if ($input->getOption('types')) {
$options = array('show_private' => true);
$options = array();
$options['filter'] = array($this, 'filterToServiceTypes');
} elseif ($input->getOption('parameters')) {
$parameters = array();
Expand All @@ -122,19 +127,20 @@ protected function execute(InputInterface $input, OutputInterface $output)
} elseif ($parameter = $input->getOption('parameter')) {
$options = array('parameter' => $parameter);
} elseif ($input->getOption('tags')) {
$options = array('group_by' => 'tags', 'show_private' => $input->getOption('show-private'));
$options = array('group_by' => 'tags');
} elseif ($tag = $input->getOption('tag')) {
$options = array('tag' => $tag, 'show_private' => $input->getOption('show-private'));
$options = array('tag' => $tag);
} elseif ($name = $input->getArgument('name')) {
$name = $this->findProperServiceName($input, $errorIo, $object, $name);
$options = array('id' => $name);
} else {
$options = array('show_private' => $input->getOption('show-private'));
$options = array();
}

$helper = new DescriptorHelper();
$options['format'] = $input->getOption('format');
$options['show_arguments'] = $input->getOption('show-arguments');
$options['show_hidden'] = $input->getOption('show-hidden');
$options['raw_text'] = $input->getOption('raw');
$options['output'] = $io;
$helper->describe($io, $object, $options);
Expand Down
Expand Up @@ -15,6 +15,7 @@
use Symfony\Component\Console\Output\OutputInterface;
use Symfony\Component\DependencyInjection\Alias;
use Symfony\Component\DependencyInjection\ContainerBuilder;
use Symfony\Component\DependencyInjection\ContainerInterface;
use Symfony\Component\DependencyInjection\Definition;
use Symfony\Component\DependencyInjection\ParameterBag\ParameterBag;
use Symfony\Component\EventDispatcher\EventDispatcherInterface;
Expand Down Expand Up @@ -230,17 +231,21 @@ protected function resolveServiceDefinition(ContainerBuilder $builder, $serviceI
return $builder->getAlias($serviceId);
}

if ('service_container' === $serviceId) {
return (new Definition(ContainerInterface::class))->setPublic(true)->setSynthetic(true);
}

// the service has been injected in some special way, just return the service
return $builder->get($serviceId);
}

/**
* @param ContainerBuilder $builder
* @param bool $showPrivate
* @param bool $showHidden
*
* @return array
*/
protected function findDefinitionsByTag(ContainerBuilder $builder, $showPrivate)
protected function findDefinitionsByTag(ContainerBuilder $builder, $showHidden)
{
$definitions = array();
$tags = $builder->findTags();
Expand All @@ -250,7 +255,7 @@ protected function findDefinitionsByTag(ContainerBuilder $builder, $showPrivate)
foreach ($builder->findTaggedServiceIds($tag) as $serviceId => $attributes) {
$definition = $this->resolveServiceDefinition($builder, $serviceId);

if (!$definition instanceof Definition || !$showPrivate && !$definition->isPublic()) {
if ($showHidden xor '.' === ($serviceId[0] ?? null)) {
continue;
}

Expand Down
Expand Up @@ -63,10 +63,10 @@ protected function describeContainerParameters(ParameterBag $parameters, array $
*/
protected function describeContainerTags(ContainerBuilder $builder, array $options = array())
{
$showPrivate = isset($options['show_private']) && $options['show_private'];
$showHidden = isset($options['show_hidden']) && $options['show_hidden'];
$data = array();

foreach ($this->findDefinitionsByTag($builder, $showPrivate) as $tag => $definitions) {
foreach ($this->findDefinitionsByTag($builder, $showHidden) as $tag => $definitions) {
$data[$tag] = array();
foreach ($definitions as $definition) {
$data[$tag][] = $this->getContainerDefinitionData($definition, true);
Expand Down Expand Up @@ -100,7 +100,7 @@ protected function describeContainerService($service, array $options = array(),
protected function describeContainerServices(ContainerBuilder $builder, array $options = array())
{
$serviceIds = isset($options['tag']) && $options['tag'] ? array_keys($builder->findTaggedServiceIds($options['tag'])) : $builder->getServiceIds();
$showPrivate = isset($options['show_private']) && $options['show_private'];
$showHidden = isset($options['show_hidden']) && $options['show_hidden'];
$omitTags = isset($options['omit_tags']) && $options['omit_tags'];
$showArguments = isset($options['show_arguments']) && $options['show_arguments'];
$data = array('definitions' => array(), 'aliases' => array(), 'services' => array());
Expand All @@ -112,14 +112,14 @@ protected function describeContainerServices(ContainerBuilder $builder, array $o
foreach ($this->sortServiceIds($serviceIds) as $serviceId) {
$service = $this->resolveServiceDefinition($builder, $serviceId);

if ($showHidden xor '.' === ($serviceId[0] ?? null)) {
continue;
}

if ($service instanceof Alias) {
if ($showPrivate || ($service->isPublic() && !$service->isPrivate())) {
$data['aliases'][$serviceId] = $this->getContainerAliasData($service);
}
$data['aliases'][$serviceId] = $this->getContainerAliasData($service);
} elseif ($service instanceof Definition) {
if (($showPrivate || ($service->isPublic() && !$service->isPrivate()))) {
$data['definitions'][$serviceId] = $this->getContainerDefinitionData($service, $omitTags, $showArguments);
}
$data['definitions'][$serviceId] = $this->getContainerDefinitionData($service, $omitTags, $showArguments);
} else {
$data['services'][$serviceId] = get_class($service);
}
Expand Down
Expand Up @@ -82,10 +82,10 @@ protected function describeContainerParameters(ParameterBag $parameters, array $
*/
protected function describeContainerTags(ContainerBuilder $builder, array $options = array())
{
$showPrivate = isset($options['show_private']) && $options['show_private'];
$showHidden = isset($options['show_hidden']) && $options['show_hidden'];
$this->write("Container tags\n==============");

foreach ($this->findDefinitionsByTag($builder, $showPrivate) as $tag => $definitions) {
foreach ($this->findDefinitionsByTag($builder, $showHidden) as $tag => $definitions) {
$this->write("\n\n".$tag."\n".str_repeat('-', strlen($tag)));
foreach ($definitions as $serviceId => $definition) {
$this->write("\n\n");
Expand Down Expand Up @@ -119,9 +119,9 @@ protected function describeContainerService($service, array $options = array(),
*/
protected function describeContainerServices(ContainerBuilder $builder, array $options = array())
{
$showPrivate = isset($options['show_private']) && $options['show_private'];
$showHidden = isset($options['show_hidden']) && $options['show_hidden'];

$title = $showPrivate ? 'Public and private services' : 'Public services';
$title = $showHidden ? 'Hidden services' : 'Services';
if (isset($options['tag'])) {
$title .= ' with tag `'.$options['tag'].'`';
}
Expand All @@ -138,14 +138,14 @@ protected function describeContainerServices(ContainerBuilder $builder, array $o
foreach ($this->sortServiceIds($serviceIds) as $serviceId) {
$service = $this->resolveServiceDefinition($builder, $serviceId);

if ($showHidden xor '.' === ($serviceId[0] ?? null)) {
continue;
}

if ($service instanceof Alias) {
if ($showPrivate || ($service->isPublic() && !$service->isPrivate())) {
$services['aliases'][$serviceId] = $service;
}
$services['aliases'][$serviceId] = $service;
} elseif ($service instanceof Definition) {
if (($showPrivate || ($service->isPublic() && !$service->isPrivate()))) {
$services['definitions'][$serviceId] = $service;
}
$services['definitions'][$serviceId] = $service;
} else {
$services['services'][$serviceId] = $service;
}
Expand Down
Expand Up @@ -122,15 +122,15 @@ protected function describeContainerParameters(ParameterBag $parameters, array $
*/
protected function describeContainerTags(ContainerBuilder $builder, array $options = array())
{
$showPrivate = isset($options['show_private']) && $options['show_private'];
$showHidden = isset($options['show_hidden']) && $options['show_hidden'];

if ($showPrivate) {
$options['output']->title('Symfony Container Public and Private Tags');
if ($showHidden) {
$options['output']->title('Symfony Container Hidden Tags');
} else {
$options['output']->title('Symfony Container Public Tags');
$options['output']->title('Symfony Container Tags');
}

foreach ($this->findDefinitionsByTag($builder, $showPrivate) as $tag => $definitions) {
foreach ($this->findDefinitionsByTag($builder, $showHidden) as $tag => $definitions) {
$options['output']->section(sprintf('"%s" tag', $tag));
$options['output']->listing(array_keys($definitions));
}
Expand Down Expand Up @@ -165,13 +165,13 @@ protected function describeContainerService($service, array $options = array(),
*/
protected function describeContainerServices(ContainerBuilder $builder, array $options = array())
{
$showPrivate = isset($options['show_private']) && $options['show_private'];
$showHidden = isset($options['show_hidden']) && $options['show_hidden'];
$showTag = isset($options['tag']) ? $options['tag'] : null;

if ($showPrivate) {
$title = 'Symfony Container Public and Private Services';
if ($showHidden) {
$title = 'Symfony Container Hidden Services';
} else {
$title = 'Symfony Container Public Services';
$title = 'Symfony Container Services';
}

if ($showTag) {
Expand All @@ -189,12 +189,14 @@ protected function describeContainerServices(ContainerBuilder $builder, array $o

foreach ($serviceIds as $key => $serviceId) {
$definition = $this->resolveServiceDefinition($builder, $serviceId);

// filter out hidden services unless shown explicitly
if ($showHidden xor '.' === ($serviceId[0] ?? null)) {
unset($serviceIds[$key]);
continue;
}

if ($definition instanceof Definition) {
// filter out private services unless shown explicitly
if (!$showPrivate && (!$definition->isPublic() || $definition->isPrivate())) {
unset($serviceIds[$key]);
continue;
}
if ($showTag) {
$tags = $definition->getTag($showTag);
foreach ($tags as $tag) {
Expand All @@ -208,11 +210,6 @@ protected function describeContainerServices(ContainerBuilder $builder, array $o
}
}
}
} elseif ($definition instanceof Alias) {
if (!$showPrivate && (!$definition->isPublic() || $definition->isPrivate())) {
unset($serviceIds[$key]);
continue;
}
}
}

Expand Down
Expand Up @@ -58,7 +58,7 @@ protected function describeContainerParameters(ParameterBag $parameters, array $
*/
protected function describeContainerTags(ContainerBuilder $builder, array $options = array())
{
$this->writeDocument($this->getContainerTagsDocument($builder, isset($options['show_private']) && $options['show_private']));
$this->writeDocument($this->getContainerTagsDocument($builder, isset($options['show_hidden']) && $options['show_hidden']));
}

/**
Expand All @@ -78,7 +78,7 @@ protected function describeContainerService($service, array $options = array(),
*/
protected function describeContainerServices(ContainerBuilder $builder, array $options = array())
{
$this->writeDocument($this->getContainerServicesDocument($builder, isset($options['tag']) ? $options['tag'] : null, isset($options['show_private']) && $options['show_private'], isset($options['show_arguments']) && $options['show_arguments'], isset($options['filter']) ? $options['filter'] : null));
$this->writeDocument($this->getContainerServicesDocument($builder, isset($options['tag']) ? $options['tag'] : null, isset($options['show_hidden']) && $options['show_hidden'], isset($options['show_arguments']) && $options['show_arguments'], isset($options['filter']) ? $options['filter'] : null));
}

/**
Expand Down Expand Up @@ -231,12 +231,12 @@ private function getContainerParametersDocument(ParameterBag $parameters): \DOMD
return $dom;
}

private function getContainerTagsDocument(ContainerBuilder $builder, bool $showPrivate = false): \DOMDocument
private function getContainerTagsDocument(ContainerBuilder $builder, bool $showHidden = false): \DOMDocument
{
$dom = new \DOMDocument('1.0', 'UTF-8');
$dom->appendChild($containerXML = $dom->createElement('container'));

foreach ($this->findDefinitionsByTag($builder, $showPrivate) as $tag => $definitions) {
foreach ($this->findDefinitionsByTag($builder, $showHidden) as $tag => $definitions) {
$containerXML->appendChild($tagXML = $dom->createElement('tag'));
$tagXML->setAttribute('name', $tag);

Expand Down Expand Up @@ -269,7 +269,7 @@ private function getContainerServiceDocument($service, string $id, ContainerBuil
return $dom;
}

private function getContainerServicesDocument(ContainerBuilder $builder, string $tag = null, bool $showPrivate = false, bool $showArguments = false, callable $filter = null): \DOMDocument
private function getContainerServicesDocument(ContainerBuilder $builder, string $tag = null, bool $showHidden = false, bool $showArguments = false, callable $filter = null): \DOMDocument
{
$dom = new \DOMDocument('1.0', 'UTF-8');
$dom->appendChild($containerXML = $dom->createElement('container'));
Expand All @@ -283,7 +283,7 @@ private function getContainerServicesDocument(ContainerBuilder $builder, string
foreach ($this->sortServiceIds($serviceIds) as $serviceId) {
$service = $this->resolveServiceDefinition($builder, $serviceId);

if (($service instanceof Definition || $service instanceof Alias) && !($showPrivate || ($service->isPublic() && !$service->isPrivate()))) {
if ($showHidden xor '.' === ($serviceId[0] ?? null)) {
continue;
}

Expand Down
Expand Up @@ -134,7 +134,7 @@ public static function getServiceProvider(ContainerBuilder $container, $name)
if ($usedEnvs || preg_match('#^[a-z]++://#', $name)) {
$dsn = $name;

if (!$container->hasDefinition($name = 'cache_connection.'.ContainerBuilder::hash($dsn))) {
if (!$container->hasDefinition($name = '.cache_connection.'.ContainerBuilder::hash($dsn))) {
$definition = new Definition(AbstractAdapter::class);
$definition->setPublic(false);
$definition->setFactory(array(AbstractAdapter::class, 'createConnection'));
Expand Down

0 comments on commit 833909b

Please sign in to comment.