【问题标题】:Argument passed to controller must be an instance of ContainerInterface, instance of appDevDebugProjectContainer given传递给控制器​​的参数必须是 ContainerInterface 的实例,给定 appDevDebugProjectContainer 的实例
【发布时间】:2015-03-12 21:06:28
【问题描述】:

为什么会出现这个错误?

可捕获的致命错误:传递给 Application\Sonata\ProductBundle\Controller\ProductAdminController::__construct() 的参数 1 必须是 ContainerInterface 的实例,给定 appDevDebugProjectContainer 的实例

这是我的 services.yml:

services:
    product_admin_controller:
      class: Application\Sonata\ProductBundle\Controller\ProductAdminController
      arguments: ["@service_container"]
      tags:
            - { name: doctrine.event_listener, event: postLoad, connection: default  }

还有我的控制器:

class ProductAdminController extends Controller
{
    protected $container;

    public function __construct(\ContainerInterface $container)
    {
        $this->container = $container;
    }
}

【问题讨论】:

  • 这似乎是Symfony 的经典控制器和控制器即服务概念的混合体。为什么你们既要扩展 Controller 又要通过 __construct 传递 Container
  • 这是一个命名空间问题。使用 Symfony\Component\DependencyInjection\ContainerInterface; __construct(ContainerInterface。你真的应该使用 ContainerAware 接口。更好的是,注入你的特定依赖项而不是完整的容器。
  • 感谢大家的帮助。主要目标是覆盖 orm 产品类并使用 mongodb odm 驱动的变体对象对其进行扩展。我尝试从第 32 页复制到以下内容 (fr.slideshare.net/jwage/…)。所以第一次尝试是注入 EntityManager (stackoverflow.com/questions/20587354/…) 但我无法做到没有错误所以我尝试了 (stackoverflow.com/questions/22128402/…)

标签: symfony dependency-injection sonata


【解决方案1】:

您必须通过“调用”选项注入容器,而不是我认为的参数:

services:
    product_admin_controller:
      class: Application\Sonata\ProductBundle\Controller\ProductAdminController
      arguments: ["@another_service_you_need"]
      tags:
            - { name: doctrine.event_listener, event: postLoad, connection: default  }
      calls:
            -   [ setContainer,["@service_container"] ]

另外,不要忘记在你的监听器类中创建公共方法“setContainer()”。

【讨论】:

    【解决方案2】:

    首先,您为什么要尝试使用 __constract()?相反,您必须使用将 ContainerInterface $container 作为参数的 setContainer() 方法,它应该如下所示:

    <?php
    ...
    use Symfony\Bundle\FrameworkBundle\Controller\Controller;
    use Symfony\Component\DependencyInjection\ContainerInterface;
    
    ...
    class YourClass extends Controller
    {
    
        public function setContainer(ContainerInterface $container = null)
        {
            // your stuff
        }
    }
    

    第二个问题:你需要将容器注入控制器做什么?您可以使用 $this->get('{service_id}') 语句调用任何服务,而不是直接调用容器。

    【讨论】:

    • 我使用 __construct() 函数,因为我想要制作的 mongoDB «extension» 是一种一般行为。我希望 mongoDB 变体对象始终扩展 mysql 产品对象。到目前为止,我设法通过服务将 EntityManager(按事先计划)传递给函数,但是,因为该类被调用了两次,第一次,我的 EntityManager $em 是一个对象,第二次是 null...我不明白为什么?
    • 因为这是最好的方法吗?
    • 对不起,但我认为“因为 mongoDB «扩展»”并没有解释什么。我仍然认为您必须将服务容器或实体管理器注入控制器。
    猜你喜欢
    • 2016-10-20
    • 2015-10-16
    • 1970-01-01
    • 2015-05-11
    • 1970-01-01
    • 1970-01-01
    • 2017-04-06
    • 1970-01-01
    • 2017-12-24
    相关资源
    最近更新 更多