schmittjoh / JMSDiExtraBundle

Provides Advanced Dependency Injection Features for Symfony2
http://jmsyst.com/bundles/JMSDiExtraBundle
330 stars 130 forks source link

Inheritance bug #195

Open phackwer opened 9 years ago

phackwer commented 9 years ago

I'm trying to extend a parent class and add a new parameter at the constructor, but, for some weird reason, it seems to map the parameter duplicated, and my arguments keep receiving the parameters in the wrong order. I mean, here is the parent class constructor:

/**
 * @DI\InjectParams({
 *     "dto" = @DI\Inject("servicedto"),
 *     "entityManager" = @DI\Inject("doctrine.orm.entity_manager"),
 * })
 */
public function __construct(ServiceDto $dto, EntityManager $entityManager = null)
{

Now, the extended constructor:

/**
 * @DI\InjectParams({
 *     "dto" = @DI\Inject("servicedto"),
 *     "entityManager" = @DI\Inject("doctrine.orm.entity_manager"),
 *     "container" = @DI\Inject("service_container"),
 * })
 */
public function __construct(ServiceDto $dto, EntityManager $entityManager, Container $container)
{

By typing the $container I get a fatal error, because it receives again ServiceDto instance instead of container. So, I decided to removbe typing and them I var_dumped the response of func_get_args().

The result was this array of arguments:

array(5) { [0] => class Defesa\BizlayBundle\Service\ServiceDto#3 (4) { ... [1] => class EntityManager552541530cbdb_546a8d27f194334ee012bfe64f629947b07e4919CG\Doctrine\ORM\EntityManager#371 (12) { ... [2] => class Defesa\BizlayBundle\Service\ServiceDto#3 (4) { ... [3] => class EntityManager552541530cbdb_546a8d27f194334ee012bfe64f629947b07e4919CG\Doctrine\ORM\EntityManager#371 (12) { ... [4] => class appDevDebugProjectContainer#296 (11) { ...

THE CONTAINER APPEARS IN FIFTH POSITION?

Hehehehe. So, I figured out what happens. For some reason, when a service extend another, the parent constructor is being merged in front of the extended constructor. Simple as it.

Any idea on what to do to fix it? I suppose that ignore the parent constructor when a new one is created should be the best solution.

phackwer commented 9 years ago

Something happened today: now inheritance completily stopped working! Only the parent methods are goindo to the Container cache!

It's really a problem...

daviddeutsch commented 9 years ago

Ran into the same issue with a Controller. Curiously, injecting properties directly in the object works for controllers that inherit objects:

class MyController extends ParentController
{
    /**
     * @DI\Inject("my.service")
     *
     * @var myService
     */
    private $myService;

    // All properties from ParentController::__construct() work just fine
rejsmont commented 9 years ago

+1 but actually this issue is documented in the bundle's docs: "Note: Constructor Injection is not possible when a parent definition also defines a constructor which is configured for injection."

phackwer commented 8 years ago

Documenting a buggy and odd behaviour doesn't make it right. Te library is breaking PHP's inheritance. It could be easily fixed by not reading all the chain of constructors.