Created
February 26, 2015 11:03
-
-
Save webdevilopers/461ff76b45046137f968 to your computer and use it in GitHub Desktop.
Doctrine ORM custom Aware Filter and Event in Symfony
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<?php | |
namespace Plusquam\Bundle\ContractBundle\Filter; | |
use Doctrine\ORM\Query\Filter\SQLFilter; | |
use Doctrine\ORM\Mapping\ClassMetadata; | |
use Doctrine\Common\Annotations\Reader; | |
class CompartmentFilter extends SQLFilter | |
{ | |
protected $reader; | |
public function setAnnotationReader(Reader $reader) | |
{ | |
$this->reader = $reader; | |
} | |
public function addFilterConstraint(ClassMetadata $targetEntity, $targetTableAlias) | |
{ | |
if (empty($this->reader)) { | |
return ''; | |
} | |
// The Doctrine filter is called for any query on any entity | |
// Check if the current entity is "compartment aware" (marked with an annotation) | |
$compartmentAware = $this->reader->getClassAnnotation( | |
$targetEntity->getReflectionClass(), | |
'Plusquam\\Bundle\\ContractBundle\\Annotation\\CompartmentAware' | |
); | |
if (!$compartmentAware) { | |
return ''; | |
} | |
// @see http://stackoverflow.com/questions/12354285/how-can-i-implemented-a-doctrine2-filter-based-on-a-relation | |
return $targetTableAlias.'.compartment_id = ' . $this->getParameter('compartment_id'); // getParameter applies quoting automatically | |
} | |
} |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<?php | |
namespace Plusquam\Bundle\CompartmentBundle\EventListener; | |
use Doctrine\ORM\Event\LifecycleEventArgs; | |
use Doctrine\Common\Annotations\Reader; | |
use Symfony\Component\Security\Core\Authentication\Token\Storage\TokenStorageInterface; | |
class CompartmentPersister | |
{ | |
private $tokenStorage; | |
public function __construct(Reader $reader, TokenStorageInterface $tokenStorage) | |
{ | |
$this->reader = $reader; | |
$this->tokenStorage = $tokenStorage; | |
} | |
public function prePersist(LifecycleEventArgs $args) | |
{ | |
$entity = $args->getEntity(); | |
// The Doctrine filter is called for any query on any entity | |
// Check if the current entity is "compartment aware" (marked with an annotation) | |
$object = new \ReflectionClass($entity); | |
$compartmentAware = $this->reader->getClassAnnotation( | |
$object, | |
'Plusquam\\Bundle\\ContractBundle\\Annotation\\CompartmentAware' | |
); | |
if ($compartmentAware) { | |
$user = $this->tokenStorage->getToken()->getUser(); | |
$compartment = $user->getCompartment(); | |
$entity->setCompartment($compartment); | |
} | |
} | |
} |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
doctrine: | |
orm: | |
filters: | |
compartment_filter: | |
class: Plusquam\Bundle\ContractBundle\Filter\CompartmentFilter | |
enabled: true |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<?php | |
namespace Plusquam\Bundle\ContractBundle\Entity; | |
use Plusquam\Bundle\ContractBundle\Annotation\CompartmentAware; | |
use Doctrine\ORM\Mapping as ORM; | |
/** | |
* @ORM\Entity | |
* @ORM\Table(name="contracts") | |
* CompartmentAware(compartmentFieldName="compartment_id") | |
* @CompartmentAware | |
*/ | |
class Contract | |
{ | |
/** | |
* @ORM\Id | |
* @ORM\Column(type="integer") | |
* @ORM\GeneratedValue(strategy="AUTO") | |
* | |
* @GRID\Column(field="id", visible=false) | |
*/ | |
private $id; | |
} |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
services: | |
qis.listener.compartmentPersister: | |
class: Plusquam\Bundle\CompartmentBundle\EventListener\CompartmentPersister | |
arguments: | |
- "@annotation_reader" | |
- "@security.token_storage" | |
tags: | |
- { name: doctrine.event_listener, event: prePersist } |
Yep, it seems to come from the article I wrote about Doctrine filters and annotations and it works really fine (in production for a large application with several kind of "something aware" entities) 😃
Indeed your post was an inspiration for this @michaelperrin. I was looking for a solution that would not only filter
the entities for a column but also persist it.
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
See:
http://stackoverflow.com/questions/12354285/how-can-i-implemented-a-doctrine2-filter-based-on-a-relation
@stevelacey
@elnur