后台任务Symfony

时间:2019-09-10 07:04:50

标签: php symfony symfony4

我想要做的是与当前请求分开运行Symfony命令。

目标:从PDF生成缩略图

问题:我不想等到生成完成后再向用户发送响应。

    public function __invoke($myparam)
    {
        $command = sprintf(
            'php %s/bin/console ps:media:generate-thumbnail %s %s &',
            $this->kernel->getProjectDir(),
            'destinationPath',
            'sourcePath'
        );

        exec($command);
    }

问题是,服务器在发送响应之前仍然等待命令完成

3 个答案:

答案 0 :(得分:2)

因此,exec函数正在等待stdio流,因此您只需要在其他地方重新分配它,/ dev / null很酷^ _ ^

public function __invoke($myparam)
    {
        $command = sprintf(
            'php %s/bin/console ps:media:generate-thumbnail %s %s > /dev/null &',
            $this->kernel->getProjectDir(),
            'destinationPath',
            'sourcePath'
        );

        exec($command);
    }

答案 1 :(得分:1)

如果您使用的是PHP FPM,则在Symfony上处理此类要求的一种好方法是在kernel.terminate事件上使用侦听器。从文档中:

  

在发送响应之后(执行handle()方法之后)调度此事件。执行不需要完成才能发送响应的慢速或复杂任务(例如发送电子邮件)很有用。

除了编写侦听器之外,还必须在$ response-> send()调用之后,将代码段添加到前端控制器中

$response->send(); 
$kernel->terminate($request, $response);

您可以在symfony文档中找到更多信息

https://symfony.com/doc/current/components/http_kernel.html#component-http-kernel-kernel-terminate

答案 2 :(得分:1)

您可以使用Cocur Background Progress库来管理后台进度

$command = sprintf(
     'exec php %s/bin/console ps:media:generate-thumbnail %s %s &',
     $this->kernel->getProjectDir(),
     'destinationPath',
     'sourcePath'
);

$process = new BackgroundProcess($command);

$process->run();