4

我需要让教义在我的助手内部工作,我试图像我通常在控制器中那样使用:

$giftRepository = $this->getDoctrine( )->getRepository( 'DonePunctisBundle:Gift' );

但这给了我:

致命错误:在 /VAR/WWW/VHOSTS/PUNCTIS.COM/HTTPDOCS/SRC/DONE/PUNCTISBUNDLE/HELPER/UTILITYHELPER.PH 中调用未定义的方法 DONE\PUNCTISBUNDLE\HELPER\UTILITYHELPER::GETDOCTRIN()

我在这里缺少什么?

编辑:

服务文件

services:
    templating.helper.utility:
        class: Done\PunctisBundle\Helper\UtilityHelper
        arguments: [@service_container]
        tags:
            - { name: templating.helper, alias: utility }

帮助文件的第一行

<?php
namespace Done\PunctisBundle\Helper;

use Symfony\Component\Templating\Helper\Helper;
use Symfony\Component\Templating\EngineInterface;



class UtilityHelper extends Helper {

    /*
     * Dependency injection
     */

    private $container;

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

2 回答 2

10

这里的问题是您的 Helper 类不是容器感知的;也就是说,它不知道 Symfony 已加载的所有服务(独白、树枝……和教义)。

您可以通过将“教义”传递给它来解决此问题。这被称为依赖注入,它是使 Symfony 很棒的核心内容之一。以下是它的工作原理:

首先,为您的 Helper 类提供一个存放 Doctrine 服务的地方,并在 Helper 的构造函数中要求它:

class UtilityHelper
{
    private $doctrine;

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

    public function doSomething()
    {
        // Do something here
    }
}

然后,您使用 services.yml 来定义 Symfony 应该如何构造该 Helper 实例:

services:
    helper:
        class: Done\PunctisBundle\Helper\UtilityHelper
        arguments: [@doctrine]

在这种情况下,@doctrine是一个占位符,表示“在此处插入 Doctrine 服务”。

因此,现在,在您的 Controller 或任何其他可感知容器的东西中,您可以通过 Helper 类访问 Doctrine,如下所示:

class SomeController()
{
    public function someAction()
    {
        $this->get("helper")->doctrine->getRepository(...);
    }
}

编辑

查看您的编辑后,您似乎将整个服务容器注入到 Helper 类中。这不是最佳实践——你应该只注入你需要的东西。但是,您仍然可以这样做:

服务.yml

services:
    helper:
        class: Done\PunctisBundle\Helper\UtilityHelper
        arguments: [@service_container]

UtilityHelper.php

class UtilityHelper
{
    private $container;

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

    public function doSomething()
    {
        // This won't work, because UtilityHelper doesn't have a getDoctrine() method:
        // $this->getDoctrine()->getRepository(...)

        // Instead, think about what you have access to...
        $container = $this->container;

        // Now, you need to get Doctrine

        // This won't work... getDoctrine() is a shortcut method, available only in a Controller
        // $container->getDoctrine()->getRepository(...)

        $container->get("doctrine")->getRepository(...)  
    }
}

我在那里添加了一些评论,突出了一些常见的陷阱。希望这可以帮助。

于 2013-03-21T15:58:35.177 回答
0

在 Helper、Services 等中,您不能像在操作中那样使用它。您需要通过 conf 文件(services.yml 或 *.xml)中的服务描述将它作为参数传递给您的 Helper。

例子:

  services:
   %service_name%:
    class: %path_to_youre_helper_class%
    arguments: [@doctrine.orm.entity_manager]
    tags:
        - { name: %name% }

并且不要忘记在你的 Helper 的 __construct 中捕获它。

例子:

use Doctrine\ORM\EntityManager;
....    

private $em;
public function __construct(EntityManager $em)
{
  $this->em = $em;
}

你可以像这样使用它:

public function myMethod()
{
  $repo = $this->em->getRepository('DonePunctisBundle:Gift');
}
于 2013-03-21T15:51:47.547 回答