2014-03-31 64 views
0

所以,現在,我得到我的每一個動作經理我控制器上這樣的:的Symfony,獲得getManager()到控制器

$em = $this->getDoctrine()->getManager(); 

有沒有更好的方式來做到這一點?使用__construct和attribut $ em?不知道?我想減少我的代碼的大小..謝謝!

回答

1

可以重載setContainer方法在你的子類,並設置經理作爲一個階級屬性:

class MyController extends Controller 
{ 
    protected $manager; 

    public function setContainer(ContainerInterface $container = null) 
    { 
     $this->manager = $container->getDoctrine()->getManager(); 
    } 
} 

當然,如果你發現使用經理了很多方法自己,也許是時候把所有的邏輯放到一個服務中,並使用適當的依賴注入。

1

一種方式做到這一點:

創建私有方法:

private function manager() 
{ 
    return $this->getDoctrine()->getManager(); 
} 

然後,在你的行動:

$em = $this->manager(); 

或直接:

$this->manager()->persist(); 
1

如果您真的想保持你的控制器精簡,也可以編寫你的模型管理器。但這不是新的,也不是我的想法。你可以在互聯網上找到一些相同的解決方案。

讓我們稱我們的實體「評論」和控制器「CommentController」。

1)我們ModelMananger是針對以下接口實現:

<?php 

namespace Sg\ExampleBundle\Doctrine\ModelManager; 

interface ModelManagerInterface 
{ 
    /** 
    * Creates an empty object instance. 
    * 
    * @return object 
    */ 
    function create(); 

    /** 
    * Saves an object. 
    * 
    * @param object $object An object instance 
    * @param boolean $andFlush Whether to flush the changes (default true) 
    * 
    * @return void 
    */ 
    function save($object, $andFlush = true); 

    /** 
    * Removes an object. 
    * 
    * @param object $object An object instance 
    * @param boolean $andFlush Whether to flush the changes (default true) 
    * 
    * @return void 
    */ 
    function remove($object, $andFlush = true); 

    /** 
    * Finds many objects by the given criteria. 
    * 
    * @param array $criteria 
    * 
    * @return array 
    */ 
    function findBy(array $criteria = array()); 

    /** 
    * Finds one object by the given criteria. 
    * 
    * @param array $criteria 
    * 
    * @return object|null 
    */ 
    function findOneBy(array $criteria = array()); 

    /** 
    * Finds an object by its primary key/identifier. 
    * 
    * @param mixed $id The identifier 
    * 
    * @return object 
    */ 
    function find($id); 

    /** 
    * Write all changes to the database. 
    * 
    * @return void 
    */ 
    function flushAllChanges(); 

    /** 
    * Returns the objects's fully qualified class name. 
    * 
    * @return string 
    */ 
    function getClass(); 
} 

2)現在我用一個抽象類來實現共同的功能:

<?php 

namespace Sg\ExampleBundle\Doctrine\ModelManager; 

use Doctrine\ORM\EntityManager; 
use Doctrine\ORM\EntityRepository; 

abstract class AbstractModelManager implements ModelManagerInterface 
{ 
    /** 
    * The fully qualified class name. 
    * 
    * @var string 
    */ 
    protected $class; 

    /** 
    * @var EntityManager 
    */ 
    protected $em; 

    /** 
    * @var EntityRepository 
    */ 
    protected $repository; 


    //------------------------------------------------- 
    // Ctor. 
    //------------------------------------------------- 

    /** 
    * Ctor. 
    * 
    * @param EntityManager $em An EntityManager instance 
    * @param string  $class The class name 
    */ 
    public function __construct(EntityManager $em, $class) 
    { 
     $this->em = $em; 
     $this->repository = $em->getRepository($class); 

     $metadata = $em->getClassMetadata($class); 
     $this->class = $metadata->getName(); 
    } 


    //------------------------------------------------- 
    // ModelManagerInterface 
    //------------------------------------------------- 

    /** 
    * {@inheritDoc} 
    */ 
    public function create() 
    { 
     $class = $this->class; 
     $object = new $class(); 

     return $object; 
    } 

    /** 
    * {@inheritDoc} 
    */ 
    public function save($object, $andFlush = true) 
    { 
     $this->em->persist($object); 

     if (true === $andFlush) { 
      $this->flushAllChanges(); 
     } 
    } 

    /** 
    * {@inheritDoc} 
    */ 
    public function remove($object, $andFlush = true) 
    { 
     $this->em->remove($object); 

     if (true === $andFlush) { 
      $this->flushAllChanges(); 
     } 
    } 

    /** 
    * {@inheritDoc} 
    */ 
    public function findBy(array $criteria = array()) 
    { 
     return $this->repository->findBy($criteria); 
    } 

    /** 
    * {@inheritDoc} 
    */ 
    public function findOneBy(array $criteria = array()) 
    { 
     return $this->repository->findOneBy($criteria); 
    } 

    /** 
    * {@inheritDoc} 
    */ 
    public function find($id) 
    { 
     return $this->repository->find($id); 
    } 

    /** 
    * {@inheritDoc} 
    */ 
    public function flushAllChanges() 
    { 
     $this->em->flush(); 
    } 

    /** 
    * {@inheritDoc} 
    */ 
    public function getClass() 
    { 
     return $this->class; 
    } 
} 

3)特殊功能來在CommentModelManager :

<?php 

namespace Sg\ExampleBundle\Doctrine\ModelManager; 

use Sg\ExampleBundle\Doctrine\ModelManager\AbstractModelManager as BaseModelManager; 
use Sg\ExampleBundle\Entity\User; 

class CommentModelManager extends BaseModelManager 
{ 
    /** 
    * Find all Comments by given User. 
    * 
    * @param User $user 
    * 
    * @return mixed 
    */ 
    public function findCommentsByUser(User $user) 
    { 
     $qb = $this->repository->createQueryBuilder('c'); 
     $qb->where('c.createdBy = :user'); 
     $qb->setParameter('user', $user); 

     return $qb->getQuery()->execute(); 
    } 
} 

4)在您的s中註冊CommentModelManager ervices.yml:

services: 

# ModelManager 

sg_example.doctrine.model_manager.comment: 
    class: Sg\ExampleBundle\Doctrine\ModelManager\CommentModelManager 
    arguments: [@doctrine.orm.entity_manager, 'Sg\ExampleBundle\Entity\Comment'] 
# ... 

5)使用CommentModelManager在CommentModel這樣的:

<?php 

namespace Sg\ExampleBundle\Controller; 

use Sg\ExampleBundle\Entity\Comment; 

// ... 

class CommentController extends Controller 
{ 
    // .. 

    public function indexAction() 
    { 
     $userComments = $this->getCommentModelManager()->findCommentsByUser($this->getUser()); 

     return array(
      'entities' => $userComments 
     ); 
    } 

    /** 
    * Shortcut to return the Comment Model Manager service. 
    * 
    * @return \Sg\ChiliManBundle\Doctrine\ModelManager\ChiliModelManager 
    */ 
    protected function getCommentModelManager() 
    { 
     return $this->container->get('sg_example.doctrine.model_manager.comment'); 
    } 
}