Why do I need to extend ServiceEntityRepository in my repository? In Symfony 3.4, I always extended EntityRepository. With ServiceEntityRepository I have a strange problem described here Symfony 4. InheritanceType("JOINED") and ParamConverter. Strange phenomenon
2 Answers
You don't need to extend ServiceEntityRepository, but you should. Why? Because it allows you to use autowiring (which is a big enhancement in SF4 and a pleasure to develop with)
class ProductRepository extends ServiceEntityRepository
{
public function __construct(RegistryInterface $registry)
{
parent::__construct($registry, Product::class);
}
}
Then you can use autowiring everywhere for example:
// From product controller
public function show(?int $id, ProductRepository $repository)
{
$product = $repository->find($id);
if (!$product) {
throw $this->createNotFoundException(
'No product found for id '.$id
);
}
return new Response('Check out this great product: '.$product->getName());
}
If you don't want, no worries just use the old way:
// From product controller
public function show(?int $id, EntityManagerInterface $manager)
{
$product = $manager->getRepository(Product::class)->find($id);
// or this one but only in a controller which extend AbstractController
$product = $this->getDoctrine()->getRepository(Product::class)->find($id);
if (!$product) {
throw $this->createNotFoundException(
'No product found for id '.$id
);
}
return new Response('Check out this great product: '.$product->getName());
}

- 23,933
- 14
- 88
- 109

- 509
- 3
- 14
-
Thank you. Your solution saved a lot time. If you try using without autowiring, you have to call method **findBy[EntityProperty]**. Otherwise, you get **"Symfony entity has no field _X_. You can therefore not call _findByX_ on entities repository"** error. With auto wiring you can call your method whatever you want – Ilyas Mar 11 '21 at 13:59
I came across this when I asked the same question while watching a training video on Symfony 4. (I also took a stab at your actual problem there.)
From what I can see of the code, you don't need to use the newer ServiceEntityRepository class, but it is an improvement. All it's doing is wrapping the EntityRepository class with a modified constructor, making the arguments you need to pass in a little friendlier for the developer, and taking advantage of autowiring.
As an example, I have manually wired up my custom repositories (extending EntityRepository) in Symfony version 3 with code like this in my services.yml file:
Fully\Qualified\Namespace\MyCustomRepository:
factory: ["@doctrine.orm.entity_manager", getRepository]
arguments: [Fully\Qualified\Namespace\Entity\MyEntity]
With the newer ServiceEntityRepository class, and version 4's enhanced autowiring, I can eliminate all of those manual wiring jobs, and let the Service Container do the job.

- 731
- 6
- 15