如何将命令定义为服务
如果您正在使用 默认的 services.yaml 配置,您的命令类已经被注册为服务。太棒了!这是推荐的设置。
注意
您也可以通过配置服务并使用 console.command
标签手动将您的命令注册为服务。
例如,假设您想从您的命令中记录一些内容
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32
namespace App\Command;
use Psr\Log\LoggerInterface;
use Symfony\Component\Console\Attribute\AsCommand;
use Symfony\Component\Console\Command\Command;
use Symfony\Component\Console\Input\InputInterface;
use Symfony\Component\Console\Output\OutputInterface;
#[AsCommand(name: 'app:sunshine')]
class SunshineCommand extends Command
{
public function __construct(
private LoggerInterface $logger,
) {
// you *must* call the parent constructor
parent::__construct();
}
protected function configure(): void
{
$this
->setDescription('Good morning!');
}
protected function execute(InputInterface $input, OutputInterface $output): int
{
$this->logger->info('Waking up the sun');
// ...
return Command::SUCCESS;
}
}
如果您正在使用 默认的 services.yaml 配置,命令类将自动注册为服务并传递 $logger
参数(感谢自动装配)。换句话说,您只需要创建这个类,一切都会自动工作!您可以调用 app:sunshine
命令并开始记录日志。
警告
您在 configure()
中确实可以访问服务。但是,如果您的命令不是懒加载的,请尽量避免执行任何工作(例如进行数据库查询),因为即使您使用控制台执行不同的命令,该代码也会运行。
懒加载
要使您的命令懒加载,可以使用 PHP AsCommand
属性定义其名称
1 2 3 4 5 6 7 8
use Symfony\Component\Console\Attribute\AsCommand;
// ...
#[AsCommand(name: 'app:sunshine')]
class SunshineCommand extends Command
{
// ...
}
或者在您的服务定义中,在 console.command
标签上设置 command
属性
1 2 3 4 5 6 7
# config/services.yaml
services:
# ...
App\Command\SunshineCommand:
tags:
- { name: 'console.command', command: 'app:sunshine' }
注意
如果命令定义了别名(使用 getAliases() 方法),您必须为每个别名添加一个 console.command
标签。
就是这样。无论如何,只有在实际调用 app:sunshine
命令时,才会实例化 SunshineCommand
。
注意
当命令是懒加载时,您不需要调用 setName()
来配置命令。
警告
调用 list
命令将实例化所有命令,包括懒加载命令。但是,如果命令是 Symfony\Component\Console\Command\LazyCommand
,则不会执行底层的命令工厂。