¿Cómo creo exactamente un EntityManager personalizado en Symfony2 / Doctrine?

Nuevo chico en Symfony / Doctrine. Así que amablemente guíame

Requisito: Crear un EntityManager personalizado que anularía algunos de los métodos como eliminar (en lugar de eliminar, quiero realizar una actualización y modificar un parámetro como isValid en mi clase, para que los registros nunca se eliminen) y un descubrimiento (encontrar un registro que tiene un valor nulo es Valido) etc. y lo usa en lugar de EntityManager de Doctrine.

Empecé a leer este hilo: ¿Hay alguna manera de especificar la clase de implementación de Doctrine2 Entitymanager en Symfony2? y la respuesta del usuario2563451 no fue tan sencilla. Me perdí cuando habla de no seguir ciertos enfoques (una vez más, no hay ubicación de los archivos para modificar).

He mirado el EntityManager.php y específicamente dice que no use extender la clase EntityManager. Más bien, solicita extender EntityManagerDecorator. Al mirar el EntityManagerDecorator, no hay métodos disponibles dentro de él (como crear, persistir, etc. que encontré en EntityManager). ¿Significa que necesito crear nuevos métodos para cada una de las funciones de Entity Manager?

Dado que no hay una manera clara y definida de hacerlo, me confunde comenzar esto. También el libro de cocina Doctrine me sirve de poco ya que no tiene información para lograrlo.

Así que cualquier ayuda con respecto a la extensión de EntityManagerDecorator o EntityManager es apreciada.

Mejor si puede proporcionarme instrucciones paso a paso para lograr lo mismo.

Gracias !

Edición 1: mi requisito es usar mi EntityManager personalizado en lugar de EntityManager (EM) de Doctrine y modificar esos métodos ‘eliminar’ y ‘buscar’ según mis requisitos. No estoy seguro de si necesito reutilizar la funcionalidad proporcionada por Doc de EM o escribir desde cero.

Creo que puede confundir a un gerente con un repository.

Un EntityManager no es más que un Servicio que utiliza para administrar ese conjunto específico o una colección de entidades.

Un repository extiende \Doctrine\ORM\EntityRepository y es lo que le dice a Doctrine cómo almacenar su entidad en la base de datos.

Puede usar la combinación de estos dos para lograr lo que desea.

Por ejemplo. Tomemos nuestra entidad Foo

 class Foo { //...other properties protected $isValid; //...Getters and setters } 

Entonces tenemos un gerente para Foo.

 class FooManager { protected $class; protected $orm; protected $repo; public function __construct(ObjectManager $orm , $class) { $this->orm = $orm; $this->repo = $orm->getRepository($class); $metaData = $orm->getClassMetadata($class); $this->class = $metaData->getName(); } public function create() { $class = $this->getClass(); $foo = new $class; return $foo; } public function findBy(array $criteria) { return $this->repo->findOneBy($criteria); } public function refreshFoo(Foo $foo) { $this->orm->refresh($foo); } public function updateFoo(Foo $foo, $flush = true) { $this->orm->persist($foo); if($flush) { $this->orm->flush(); } } public function getClass() { return $this->class; } } 

Tenemos algunas funciones básicas para crear y actualizar nuestro objeto. Y ahora si desea “eliminar” sin eliminarlo realmente, puede agregar la siguiente función en el Administrador.

 public function remove(Foo $foo) { $foo->setIsValid(false); return $this->update($foo); } 

De esta manera, actualizamos los campos isValid a falso y lo conservamos en la base de datos. Y lo usarías como cualquier servicio dentro de tu controlador.

 class MyController extends Controller { public function someAction() { $fooManager = $this->get('my_foo_manager'); $newFoo = $fooManager->create(); //... $fooManager->remove($newFoo); } } 

Entonces ahora tenemos la parte eliminada.

A continuación, solo queremos encontrar entidades que sean isValid en TRUE.

Honestamente, la forma en que manejaría esto ni siquiera es modificar el hallazgo y en su lugar en su controlador

 if(!$foo->getIsValid()) { //Throw some kind of error. Or redirect to an error page. } 

Pero si quieres hacerlo de otra manera. Puedes hacer un repository.

 use Doctrine\ORM\EntityRepository; class FooRepository extends EntityRepository { public function find($id, $lockMode = LockMode::NONE, $lockVersion = null) { //Some custom doctrine query. } } 

Anulamos la función find () nativa de EntityRepository con la nuestra.

Finalmente, tenemos todo esto registrado en los lugares correctos. Para el gerente tienes que hacer un servicio.

 services: my_foo_manager: class: AppBundle\Manager\FooManager arguments: [ "@doctrine.orm.entity_manager" , 'AppBundle\Entity\Foo'] 

Y para el repository, debe especificar el repositoryClass en la definición ORM de su entidad.

 AppBundle\Entity\Foo: type: entity repositoryClass: AppBundle\Entity\FooRepository table: foos id: id: type: integer generator: {strategy: AUTO} options: {unsigned: true} fields: isValid: type: boolean 

Sabiendo todo esto, ahora puedes hacer cosas geniales con Entidades. Espero que esto haya ayudado. ¡Buena suerte!

Con respecto a sus casos de uso, en su lugar debería usar Doctrine Lifecycle Callbacks para eliminar mayúsculas y minúsculas simples del método de búsqueda en el repository de su entidad.