如何在 Symfony 中通过命名空间配置服务组

How to configure group of services by namespace in Symfony

在默认的 Symfony 5 配置中,我是这样看的:

services:
    ...
    App\:
        resource: '../src/*'
        exclude: '../src/{DependencyInjection,Entity,Exception,Migrations,Tests,Kernel.php}'
    ...
    App\Controller\:
        resource: '../src/Controller'
        tags: ['controller.service_arguments']

看起来很酷。好像我可以通过命名空间为一组服务配置一些默认设置,就像那样

    ...
    App\Service\MySpecialTaskServices\:
        resource: '../src/Service/MySpecialTaskServices/*'
        public: true
        ... other default params\args for this NS ...

但这东西不起作用:配置正确加载,但无法应用参数。

可能是我做错了什么?这是个坏主意,用一堆具有相同参数的服务堵塞 services.yaml。

我找到了一个很好的理由,那就是使用自定义标签功能。也许对其他人有帮助。

  1. 将您的服务实例化为单个 interface/abstract
  2. 在全局服务中 services.yml 添加 _instanceof 选项:块
services:
    _default:
        ....
    _instanceof:
        App\Service\MySpecialTaskServices\MySpecialTaskInterface:
            tags: ['app.public_service']
  1. 使用此处理方法定义自定义编译器传递以支持您的新标记
class PublicServicesGroupPass implements CompilerPassInterface
{
    ...
    public function process(ContainerBuilder $container): void
    {
        $services = $container->findTaggedServiceIds('app.public_service');
        foreach (array_keys($services) as $id) {
            $definition = $container->findDefinition($id);
            $definition->setPublic(true);
            // other works with params
        }
    }
    ...
}
  1. 并在你的内核中注册它们
class Kernel extends BaseKernel
{
    ...
    protected function build(ContainerBuilder $container): void
    {
        $container->addCompilerPass(new PublicServicesGroupPass());
    }
    ...
}

这工作正常。但我想让它更简单。