Symfony 2: создание службы из репозитория

Я изучаю Symfony, и я пытаюсь создать сервис, используя repository. Я создал свои репозитории и сущности из generate: entity, поэтому они должны быть в порядке.

До сих пор, что я получил в моих services.yml:

parameters: mytest.entity: TestTestBundle:Brand mytest.class: Test\TestBundle\Entity\Brand default_repository.class: Doctrine\ORM\EntityRepository services: myservice: class: %default_repository.class% factory-service: doctrine.orm.default_entity_manager factory-method: getRepository arguments: - %mytest.entity% 

Но когда я пытаюсь вызвать службу, я получаю эту ошибку:

 Catchable Fatal Error: Argument 2 passed to Doctrine\ORM\EntityRepository::__construct() must be an instance of Doctrine\ORM\Mapping\ClassMetadata, none given, called in 

Затем я попытался создать сервис, используя только объект. Мои services.yml будут выглядеть так:

 services: myservice: class: %mytest.class% factory-service: doctrine.orm.default_entity_manager factory-method: getRepository arguments: - %mytest.entity% 

Но для этого я получаю:

 Error: Call to undefined method Test\TestBundle\Entity\Brand::findAll 

Кто-нибудь знает, что я делаю неправильно?

благодаря

Вот как мы это сделали в KnpRadBundle: https://github.com/KnpLabs/KnpRadBundle/blob/develop/DependencyInjection/Definition/DoctrineRepositoryFactory.php#L9

Наконец, это должно быть:

 my_service: class: Doctrine\Common\Persistence\ObjectRepository factory_service: doctrine # this is an instance of Registry factory_method: getRepository arguments: [ %mytest.entity% ] 

ОБНОВИТЬ

Начиная с версии 2.4, doctrine позволяет переопределить фабрику репозитория по умолчанию.

Вот возможный способ реализовать его в symfony: https://gist.github.com/docteurklein/9778800

ПРЕДУПРЕЖДЕНИЕ О ДЕПРЕКАЦИИ: больше нет factory_service и factory_method . Вот как вы должны это делать, начиная с Symfony 2.6 (для Symfony 3.3+ ):

 parameters: entity.my_entity: "AppBundle:MyEntity" services: my_entity_repository: class: AppBundle\Repository\MyEntityRepository factory: ["@doctrine", getRepository] arguments: - %entity.my_entity% 

Новый метод setFactory () был введен в Symfony 2.6. Обратитесь к старым версиям синтаксиса для фабрик до 2.6.

http://symfony.com/doc/2.7/service_container/factories.html

EDIT: Похоже, они продолжают меняться, так как Symfony 3.3 появился новый синтаксис:

 # app/config/services.yml services: # ... AppBundle\Email\NewsletterManager: # call the static method factory: ['AppBundle\Email\NewsletterManagerStaticFactory', createNewsletterManager] 

Проверьте это: http://symfony.com/doc/3.3/service_container/factories.html

Возможно, вы использовали неправильные клавиши YAML. Ваша первая конфигурация работает отлично для меня, используя

  • factory_service вместо заводского обслуживания
  • factory_method вместо заводского метода

С 2017 года и Symfony 3.3+ это стало намного проще.

Примечание. Старайтесь избегать общих команд, таких как generate:entity . Они предназначены для начинающих, чтобы сделать работу над проектом быстрой. Они склонны огорчать плохую практику и очень долго менять.

Проверьте мое сообщение Как использовать repository с Doctrine as Service в Symfony для более общего описания.

К вашему коду:

1. Обновите регистрацию конфигурации, чтобы использовать автоматическую регистрацию на основе PSR-4

 # app/config/services.yml services: _defaults: autowire: true Test\TestBundle\: resource: ../../src/Test/TestBundle 

2. Состав над наследством. Создайте собственный repository без прямой зависимости от Доктрины.

 repository = $entityManager->getRepository(Brand::class); } public function findAll() { return $this->repository->findAll(); } } 

3. Использование в любой службе или controllerе через инъекцию конструктора

 use Test\TestBundle\Repository\BrandRepository; class MyController { /** * @var BrandRepository */ private $brandRepository; public function __construct(BrandRepository $brandRepository) { $this->brandRepository = $brandRepository; } public function someAction() { $allBrands = $this->brandRepository->findAll(); // ... } } 

Я конвертирую service.yml в service.xml и обновляю DependencyInjection Extension, все работает для меня. Я не знаю, почему, но yml config будет выброшен Catchable Fatal Error. Вы можете попробовать использовать конфигурацию xml для конфигурации службы.

service.yml:

 services: acme.demo.apikey_userprovider: class: Acme\DemoBundle\Entity\UserinfoRepository factory-service: doctrine.orm.entity_manager factory-method: getRepository arguments: [ AcmeDemoBundle:Userinfo ] acme.demo.apikey_authenticator: class: Acme\DemoBundle\Security\ApiKeyAuthenticator arguments: [ "@acme.demo.apikey_userprovider" ] 

service.xml:

   AcmeDemoBundle:Userinfo      

Symfony 3.3 и doctrine-bundle 1.8 существует Doctrine \ Bundle \ DoctrineBundle \ Repository \ ContainerRepositoryFactory, который помогает создавать repository в качестве службы.

пример

Что мы хотим

 $rep = $kernel->getContainer() ->get('doctrine.orm.entity_manager') ->getRepository(Brand::class); 

Описание ORM

 # Brand.orm.yaml ... repositoryClass: App\Repository\BrandRepository ... 

Описание услуг

 # service.yaml App\Repository\BrandRepository: arguments: - '@doctrine.orm.entity_manager' - '@=service("doctrine.orm.entity_manager").getClassMetadata("App\\Entity\\Brand")' tags: - { name: doctrine.repository_service } calls: - method: setDefaultLocale arguments: - '%kernel.default_locale%' - method: setRequestStack arguments: - '@request_stack' 

sf 2.6+

 parameters: mytest.entity: TestTestBundle:Brand mytest.class: Test\TestBundle\Entity\Brand default_repository.class: Doctrine\ORM\EntityRepository services: myservice: class: %default_repository.class% factory: ["@doctrine.orm.default_entity_manager", "getRepository"] arguments: - %mytest.entity% 
  • Получить URL-адрес загрузки из файла, загруженного с помощью облачных функций для Firebase
  • Хранение изображений: DB или файловая система -
  • Android создает папки во внутренней памяти
  • Как вы клонируете repository Git в определенную папку?
  • Где debug.keystore в Android Studio
  • Android-файл для сохранения на внешнем хранилище
  • Основные данные - сохранение изображений (iPhone)
  • Как проверить имя сертификата и псевдоним в файлах хранилища ключей?
  • Лучший способ хранения данных локально в .NET (C #)
  • «Не разрешено загружать локальный ресурс: file: /// C: ... jpg» Java EE Tomcat
  • Давайте будем гением компьютера.