首页 文章

如何从console参数设置config参数?

提问于
浏览
4

我是Symfony的新手 .

我试图通过控制台参数'format = json'来改变Monolog输出格式化程序 .

简而言之,我想用这样的方式运行任何控制台命令:

app/console my_command --format=json # xml / txt / my own

...以请求的格式获取LoggerInterface的输出 .

例如,我在配置中设置了默认格式化程序:

monolog:
    handlers:
        console:
            type:   console
            channels: [!event, !doctrine]
            formatter: json_formatter
services:
    json_formatter:
        class: Monolog\Formatter\JsonFormatter

当我创建一些MyEventListener :: onConsoleCommand(as described here)时,我无法更改参数包,因为它已经编译:"Impossible to call set() on a frozen ParameterBag."

Up2:在这种情况下我的服务配置如下所示:

services:
    kernel.listener.command_dispatch:
        class: My\Listener\MyEventListener
        autowire: true
        tags:
            - { name: kernel.event_listener, event: console.command }

换句话说,我可以在初始文件中注册控制台选项:

# app/console
$loader = require __DIR__.'/autoload.php';
# ...
$application->getDefinition()->addOption(
    new InputOption(
        'formatter',
        'f',
        InputOption::VALUE_OPTIONAL,
        'The logs output formatter',
        'json_formatter'
    )
);

但是我找不到在Container中更改参数包的方法 . 因为$ application-> getKernel() - > getContainer()仍然是空的 .

那么,如何从控制台输入中更改Symfony2参数?

或者,也许我可以使用一些环境参数?但是如何在YAML配置中获取环境变量?

谢谢 .

UP3: 我已经用这样的环境变量实现了目标:

SYMFONY__LOG__FORMATTER=json_formatter app/console my_command
monolog:
    handlers:
        console:
            type: console
            #...
            formatter: '%log.formatter%'

2 回答

  • 1

    修改应用程序的每个已注册命令的命令参数的唯一一点是处理 CommandEvents::COMMAND ,触发 before 已执行任何命令 . 因此,您可以修改其参数并按here所述读取它们 . 此外,此时您已编译容器,此时无法修改服务的定义 . 但是你可以获得任何服务 .

    所以我认为你最终可以得到以下处理程序:

    class LogFormatterEventListener
    {
        private $container;
        private $consoleHandler;
    
        public function __construct(ContainerInterface $container, HandlerInterface $consoleHandler)
        {
            $this->container = $container;
            $this->consoleHandler = $consoleHandler;
        }
    
        public function onConsoleCommand(ConsoleCommandEvent $event)
        {
            $inputDefinition = $event->getCommand()->getApplication()->getDefinition();
    
            $inputDefinition->addOption(
                new InputOption('logformat', null, InputOption::VALUE_OPTIONAL, 'Format of your logs', null)
            );
    
            // merge the application's input definition
            $event->getCommand()->mergeApplicationDefinition();
    
            $input = new ArgvInput();
    
            // we use the input definition of the command
            $input->bind($event->getCommand()->getDefinition());
    
            $formatter = $input->getOption('logformat');
            if ($formatter /** && $this->container->has($formatter) **/) {
                $this->consoleHandler->setFormatter(
                    $this->container->get($formatter);
                );
            }
        }
    }
    
  • 0

    这是替代解决方案(与常见兼容):

    Configuration:

    monolog:
        handlers:
            console:
                type:   console
                channels: [!event, !doctrine]
                formatter: "%log.formatter%"
    services:
        json_formatter:
            class: Monolog\Formatter\JsonFormatter
    

    Command execution:

    # colored plain text
    app/console my_command
    
    # json
    SYMFONY__LOG__FORMATTER=json_formatter app/console my_command
    

相关问题