web-dev-qa-db-ja.com

Symfony 2 EntityManagerインジェクションサービス

独自のサービスを作成し、doctrine EntityManagerをインジェクトする必要がありますが、__construct()がサービスで呼び出されていることがわかりません。インジェクションが機能しません。

コードと構成は次のとおりです。

<?php

namespace Test\CommonBundle\Services;
use Doctrine\ORM\EntityManager;

class UserService {

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

    public function __constructor(EntityManager $entityManager)
    {
        var_dump($entityManager);
        exit(); // I've never saw it happen, looks like constructor never called
        $this->em = $entityManager;
    }

    public function getUser($userId){
       var_dump($this->em ); // outputs null  
    }

}

バンドルにはservices.ymlがあります

services:
  test.common.userservice:
    class:  Test\CommonBundle\Services\UserService
    arguments: 
        entityManager: "@doctrine.orm.entity_manager"

そのような.ymlをアプリのconfig.ymlにインポートしました

imports:
    # a few lines skipped, not relevant here, i think
    - { resource: "@TestCommonBundle/Resources/config/services.yml" }

そして、コントローラーでサービスを呼び出すと

    $userservice = $this->get('test.common.userservice');
    $userservice->getUser(123);

オブジェクト(nullではない)を取得しますが、UserServiceの$this->emがnullであり、既に述べたように、UserServiceのコンストラクターが呼び出されたことはありません

もう1つ、ControllerとUserServiceは異なるバンドルになっています(プロジェクトを整理するために本当に必要です)が、それでも他のすべてがうまく機能するので、電話することもできます。

$this->get('doctrine.orm.entity_manager')

userServiceを取得し、有効な(nullではない)EntityManagerオブジェクトを取得するために使用するのと同じコントローラーで。

構成の一部またはUserServiceとDoctrine config間のリンクが欠落しているように見えます。

95
Andrey Zavarin

クラスのコンストラクターメソッドは、__construct()ではなく、__constructor()と呼ばれる必要があります。

public function __construct(EntityManager $entityManager)
{
    $this->em = $entityManager;
}
112
richsage

Symfony 2.4以降では、Constructor Injectionメソッドの引数に名前を付けることはできなくなりました。 ドキュメント によると、あなたは渡すでしょう:

services:
    test.common.userservice:
        class:  Test\CommonBundle\Services\UserService
        arguments: [ "@doctrine.orm.entity_manager" ]

そして、それらは、引数を介してリストされた順序で利用可能になります(複数ある場合)。

public function __construct(EntityManager $entityManager) {
    $this->em = $entityManager;
}
64
Chadwick Meyer

Symfony 3.3の時点で、EntityManagerは減価されています。代わりにEntityManagerInterfaceを使用してください。

namespace AppBundle\Service;

use Doctrine\ORM\EntityManagerInterface;

class Someclass {
    protected $em;

    public function __construct(EntityManagerInterface $entityManager)
    {
        $this->em = $entityManager;
    }

    public function somefunction() {
        $em = $this->em;
        ...
    }
}
16
Robert Saylor

2017年およびSymfony 3.3以降できますリポジトリをサービスとして登録、その利点をすべて備えています。

投稿を確認してください SymfonyでDoctrineを使用してリポジトリをリポジトリとして使用する方法.


特定のケースでは、チューニングを含む元のコードは次のようになります。

1.サービスまたはコントローラーで使用する

<?php

namespace Test\CommonBundle\Services;

use Doctrine\ORM\EntityManagerInterface;

class UserService
{
    private $userRepository;

    // use custom repository over direct use of EntityManager
    // see step 2
    public function __constructor(UserRepository $userRepository)
    {
        $this->userRepository = $userRepository;
    }

    public function getUser($userId)
    {
        return $this->userRepository->find($userId);
    }
}

2.新しいカスタムリポジトリを作成する

<?php

namespace Test\CommonBundle\Repository;

use Doctrine\ORM\EntityManagerInterface;

class UserRepository
{
    private $repository;

    public function __construct(EntityManagerInterface $entityManager)
    {
        $this->repository = $entityManager->getRepository(UserEntity::class);
    }

    public function find($userId)
    {
        return  $this->repository->find($userId);
    }
}

3.サービスを登録する

# app/config/services.yml
services:
    _defaults:
        autowire: true

    Test\CommonBundle\:
       resource: ../../Test/CommonBundle
7
Tomáš Votruba