如何在symfony 4中公开LoggerInterface服务

如何在symfony 4中公开LoggerInterface服务,symfony,Symfony,我希望在symfony中有Psr\Log\LoggerInterfacepublic,以便能够使用$container->get('Psr\Log\LoggerInterface')直接从容器中获取它 我尝试了以下服务。yaml: _defaults: public: true Psr\Log\LoggerInterface: public: true Psr\Log\LoggerInterface: alias: 'logger' public: true Psr\Log\Log

我希望在symfony中有
Psr\Log\LoggerInterface
public,以便能够使用
$container->get('Psr\Log\LoggerInterface')
直接从容器中获取它

我尝试了以下
服务。yaml

_defaults:
 public: true

Psr\Log\LoggerInterface:
 public: true

Psr\Log\LoggerInterface:
 alias: 'logger'
 public: true

Psr\Log\LoggerInterface:
 alias: 'monolog.logger'
 public: true

我不知道为什么重写服务如此困难。

使用$container->get()是一种糟糕的做法。它违反了许多好的软件设计原则

您应该改用构造函数注入

class Foo
{
    protected $logger;

    public function __construct(LoggerInterface $logger)
    {
        $this->logger = $logger;
    }
}

如前所述,不鼓励直接从容器访问服务。但我有点好奇如何将私人服务公之于众。我尝试了问题中列出的内容,并确认它不起作用

这可能不是最简单的方法,但编译器传递可以做到这一点:

# src/Kernel.php
# Make the kernel a compiler pass
use Psr\Log\LoggerInterface;
use Symfony\Component\DependencyInjection\Compiler\CompilerPassInterface;
class Kernel extends BaseKernel implements CompilerPassInterface
...
public function process(ContainerBuilder $container)
{
    $logger = $container->getAlias(LoggerInterface::class);
    $logger->setPublic(true);
}

# And that should do the trick, you can confirm with
bin/console debug:container Psr\Log\LoggerInterface
请注意,只有注入了完整容器的服务才能利用这一点。从AbstractController扩展的控制器只能访问少量服务


看看您是否需要控制器中的记录器,或者您是否只是想要一种“更好”的方式来完成此操作。

$container->get('logger')将获取记录器,前提是您可以访问完整的容器。您是想从控制器还是仅仅从某个服务访问记录器?每个人都说,直接使用容器是一种糟糕的做法。但是有两点。没有人知道我的处境。第二,我们不必费心在一个服务上声明构造函数参数,而这个服务实际上并不需要,但它是为它的子服务的。它没有文档。但很快,您就会这样声明属性:`/***@Option()*@var CategoryRepository*/protected$CategoryRepository;`在类init之后就有了存储库。作为记录,我说的是“不鼓励”而不是“坏”,因为当然有时候需要访问容器。根据您的评论,不确定您的选项包具体做了什么。仅供参考,这里有一个/**@required*/注释,可用于自动注入依赖项。你甚至可以把它放在一个trait中,然后任何使用该trait的类都可以不费吹灰之力获得依赖关系。
@required
听起来很有趣。你是说这个吗?这个代码是否仍然适用于3.4及更高版本?我已经添加到我的appKernel.php(我正在迁移一个旧的2.7应用程序)中,并在调试器中验证了它的运行情况,但是尽管设置了公共设置,当下次请求服务时,它仍然在私有服务列表中。编辑-是的,我只需要将服务名称更改为'logger',即$container->getAlias('logger')。哦,太简单了!