使用Symfony控制台(CTRL C)捕获终端终端/退出



我已经构建了一个命令,该命令从Internet上触发文件下载,但是由于这些文件需要由另一个组件处理,因此我们需要确保每个已下载的文件和在过去的10秒内尚未修改,是一个正确的视频,未经损坏/部分下载。

因此,我们需要找到一种方法来捕获CTRL C或命令终止并清理任何未成功下载的适用文件。

这是我到目前为止使用symfony/consolesymfony/event-dispatcher的尝试的方法:

#!/usr/bin/env php
<?php
require_once(__DIR__ . '/../vendor/autoload.php');
use SymfonyComponentConsoleApplication;
use SymfonyComponentConsoleConsoleEvents;
use SymfonyComponentConsoleEventConsoleTerminateEvent;
use SymfonyComponentEventDispatcherEventDispatcher;
use ImportExportConsoleImportCommand;
use MonologLogger;
$dotenv = new DotenvDotenv(__DIR__ . '/../');
$dotenv->load();
$logger = new Logger('console');
$dispatcher = new EventDispatcher();
$dispatcher->addListener(ConsoleEvents::TERMINATE, function (ConsoleTerminateEvent $event) {
    // gets the command that has been executed
    $command = $event->getCommand();
    var_dump($command);
});
$application = new Application("Import-Export System", 'v0.1.0-ALPHA');
$application->add(new ImportCommand($logger));
$application->setDispatcher($dispatcher);
$application->run();

但是,如果我做ctrl c。

var_dump()永远不会在控制台中显示

建议?

进行CTRL C时,实际上是在发送SIGINT,而不是SIGTERM。我能想到的最好的方法是用http://php.net/manual/en/function.pcntl-signal.php注册处理程序,并用pcntl_signal_dispatch派遣信号,示例:

pcntl_signal(SIGINT,'sigIntHandler');
function sigIntHandler() {
  // Do some stuff
}

当然,您需要根据自己的需求进行调整。请注意,您还可以将命令中的类方法推迟,因此您可以使用通用sigIntHandler()创建一个AbstractCommand,然后在构造函数中注册:

pcntl_signal(SIGINT, [$this, 'sigIntHandler']);

然后在命令的循环中使用 pcntl_signal_dispatch()(需要在每次迭代中调用(。

自Symfony 5.2以来,这是一个本机功能:https://symfony.com/blog/new-inew-inew-inew-symfony-5-2-console-signals

实现接口(signalableCommandInterface(,订阅信号并处理:

public function handleSignal(int $signal)
{
    if (SIGINT === $signal) {
        // ...
    }
    // ...
}

相关内容

  • 没有找到相关文章

最新更新