Question

I know it is not a good practice to use objectManager to get collection. However, I don't know what is the advantage of using ModelFactory ($this->mymodelFactory->create()->getCollection()) over injecting Collection class directly in to the constructor?

For example following two codes generates same results:

Using Factory:

<?php

namespace Unit4\Module6\Controller\Demo;

use Magento\Framework\App\Action\Context;
use Unit4\Module6\Model\VendorFactory;


class Index extends \Magento\Framework\App\Action\Action
{

    protected $_vendorFactory;


    public function __construct(
        Context $context,
        VendorFactory $vendorFactory,
        array $data = array()
    ) {
        parent::__construct($context, $data);
        $this->_vendorFactory = $vendorFactory;
    }




    public function execute()
    {
        $vendorModel = $this->_vendorFactory->create();
        $vendorCollection = $vendorModel->getCollection();
        var_dump($vendorCollection->getData());
    }
} 

Injecting the Collection class directly in the __construct() function:

<?php

namespace Unit4\Module6\Controller\Demo;

use Magento\Framework\App\Action\Context;
use Unit4\Module6\Model\ResourceModel\Vendor\Collection;


class Index extends \Magento\Framework\App\Action\Action
{

    protected $_collection;


    public function __construct(
        Context $context,
        Collection $collection,
        array $data = array()
    ) {
        parent::__construct($context, $data);
        $this->_collection = $collection;
    }




    public function execute()
    {
        $vendorCollection = $this->_collection;
        var_dump($vendorCollection->getData());
    }
}

So what is the advantage of using Factories here?

Was it helpful?

Solution

Since you are foremost asking for best practice: The best practice is to create the collection using factories, getCollection() is a shortcut that I would see as a relict from Magento 1.

It's not deprecated, but if you look at the code, it becomes clear that the team is not quite happy with it but also don't really deem it important:

  • A TODO comment that sits there since 0.1.0-alpha108 (12/2014)

     * @TODO MAGETWO-23541: Incorrect dependencies between Model\AbstractModel and Data\Collection\Db from Framework
    
  • Direct use of object manager:

    return $this->_resourceCollection ? clone $this
        ->_resourceCollection : \Magento\Framework\App\ObjectManager::getInstance()
        ->create(
            $this->_collectionName
        );
    

Technically there is no big difference. Although the use of clone in getCollection() might lead to subtle differences compared to always instantiating a new object.

Full source: https://github.com/magento/magento2/blame/a45e591ab7380346eb57db291e49ac96b29dfb0a/lib/internal/Magento/Framework/Model/AbstractModel.php#L489-L519

Licensed under: CC-BY-SA with attribution
Not affiliated with magento.stackexchange
scroll top