【问题标题】:Call KernelInterface in Symfony Controller在 Symfony 控制器中调用 KernelInterface
【发布时间】:2019-12-02 23:42:33
【问题描述】:

我需要从控制器运行一些 Symfony 命令,以便服务器不支持 ssh 连接。

我找到了这个 Symfony 文档 https://symfony.com/doc/3.3/console/command_in_controller.html

/**
 * @Route("/command/run")
 * @Method("POST")
 *
 * @param KernelInterface $kernel
 *
 * @return Response
 * @throws \Exception
 */
public function runCommandAction(KernelInterface $kernel)
{
    $application = new Application($kernel);
    $application->setAutoExit(false);

    $input = new ArrayInput([
        'command' => 'doctrine:schema:update',
        "--force" => true
    ]);

    $output = new BufferedOutput();
    $application->run($input, $output);

    $content = $output->fetch();

    return new Response($content);
}

这段代码几乎就像 Symfony 文档中的一个示例。

但运行代码时出现此错误。

提供的类型“Symfony\Component\HttpKernel\KernelInterface”是一个 接口,不能实例化

Symfony 版本是 3.3
PHP版本是7.1

我必须补充一点,我正在使用 FOSRest 捆绑包,但我想这应该不是问题。

我在这里做错了什么? 我错过了什么吗?

【问题讨论】:

  • 我认为您需要在 services.yaml 文件中创建一个别名。 symfony.com/doc/current/service_container/… 这是最近对 autowire 的更改。
  • 我在一个新的 S4.0 项目上尝试了您的代码,它按预期工作。我认为您必须有两个实现 KernelInterface 的服务,或者您的供应商可能需要更新。无论如何,请尝试将 Symfony\Component\HttpKernel\KernelInterface: '@kernel' 添加到您的服务文件中。
  • @Cerad 谢谢 :) 如果这有助于添加答案,我会通知您,我将提供有用的答案:) 如果您愿意,即使现​​在也可以添加。
  • @StevanTosic 看起来 FOSRestBundle 正在尝试转换您的论点,有一个未解决的问题:github.com/FriendsOfSymfony/FOSRestBundle/issues/1758
  • @Orange18947 我刚刚找到了可行的解决方案,你能检查一下吗?

标签: php symfony


【解决方案1】:

我通过在构造类中添加接口解决了这个问题。

/**
 * @var KernelInterface
 */
private $kernel;

public function __construct(KernelInterface $kernel)
{
    $this->kernel = $kernel;
}

/**
 * @Route("/command/run")
 * @Method("POST")
 *
 * @param KernelInterface $kernel
 *
 * @return Response
 * @throws \Exception
 */
public function runCommandAction()
{
    $application = new Application($this->kernel);
    $application->setAutoExit(false);

    $input = new ArrayInput([
        'command' => 'doctrine:schema:update',
        "--force" => true
    ]);

    $output = new BufferedOutput();
    $application->run($input, $output);

    $content = $output->fetch();

    return new Response($content);
}

【讨论】:

    【解决方案2】:

    我认为在控制器中获取内核的最简单方法是这样的。

    $this->get('kernel')
    

    所以不要像这样将内核作为私有成员变量添加到控制器对象中。

    $application = new Application($this->kernel);
    

    我这样做。

    $application = new Application($this->get('kernel'));
    

    此时我仍在运行 3.4。

    【讨论】:

      猜你喜欢
      • 2021-10-05
      • 1970-01-01
      • 1970-01-01
      • 2014-03-25
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多