Magento2 преимущества фабричного образца по сравнению с Magento 1

15

Magento 2 использует фабричные классы для неинъекционных препаратов.

Например, класс продукта: ProductFactory
Например, класс клиента:CustomerFactory

Я не понимаю, какой тип фабричной модели здесь?

Потому что для каждого класса связан 1 фабричный класс. Я думаю, что-то дублирует. Почему мы не должны создавать абстрактные фабрики CustomerFactoryи ProductFactoryт. Д.?

а также например:

Мы можем передать AbstractFactoryдля проверки типа вместо ProductFactoryв ProductRepositoryконструкторе класса.

Таким образом , мы можем избежать тесной связи между ProductRepositoryиProductFactory


Абстрактный Фабричный класс:

namespace Magento\Framework\ObjectManager\Code\Generator;

/**
 * Abstract Factory class 
 */
abstract class AbstractFactory 
{
    /**
     * Object Manager instance
     *
     * @var \Magento\Framework\ObjectManagerInterface
     */
    protected $_objectManager = null;

    /**
     * Instance name to create
     *
     * @var string
     */
    protected $_instanceName = null;


    /**
     * Create class instance with specified parameters
     *
     * @param array $data
     * @return \Magento\Catalog\Model\Product
     */
    public function create(array $data = array())
    {
        return $this->_objectManager->create($this->_instanceName, $data);
    }
}

Реализация фабрики:

namespace Magento\Catalog\Model;
use Magento\Framework\ObjectManager\Code\Generator\AbstractFactory;
/**
 * Factory class for @see \Magento\Catalog\Model\Product
 */
class ProductFactory extends AbstractFactory
{

    public function __construct(\Magento\Framework\ObjectManagerInterface $objectManager, $instanceName = '\\Magento\\Catalog\\Model\\Product')
    {

        $this->_objectManager = $objectManager;
        $this->_instanceName = $instanceName;
    }

}

Какова связь между менеджером объектов и фабрикой?

Существует так много цепочек объектов:

  • Например ProductRepository(здесь мы можем назвать его клиентом) требуется Productобъект.

  • Это зависит от конкретного ProductFactoryобъекта.

  • ProductFactoryобъект зависит от ObjectManagerобъекта.

  • ObjectManagerобъект зависит от объекта Factory (здесь Developer Object).

Конечно, они используют интерфейсы для слабой связи. Все еще действительно запутанный поток.

Можете ли вы дать кому-то всестороннее преимущество с заводским шаблоном Magento 2, а также чем он отличается от Magento 1?

Sivakumar
источник

Ответы:

8

Следует помнить одну вещь: мы автоматически генерируем фабричные классы, ТОЛЬКО ЕСЛИ ВЫ НЕ ОПРЕДЕЛЯЕТЕ САМОГО. Это означает, что если вам нужно творить особую магию на фабрике, вы можете это сделать. (Например, если вы хотите по какой-либо причине регистрировать каждое создание экземпляра, напишите фабрику самостоятельно, и мы не будем ее автоматически генерировать.) Если бы мы использовали один абстрактный класс фабрики для всего, это не сработало бы.

Это также может немного помочь с отладкой - вы можете увидеть реальный класс, можете установить точки останова, увидеть более значимые трассировки стека и т. Д.

Алан Кент
источник
может быть небольшой пробел .. только для проверки типа я хочу использовать абстрактный класс .. но всякий раз, когда я передаю, я хочу передать только конкретный фабричный класс.
Сивакумар
Интересно - я бы обдумал обратное. Я хотел бы передать CustomerFactory, поэтому у меня есть подсказка типа, что create () вернет Customer. С AbstractFactory я не могу использовать подсказку типа php Storm, чтобы определить тип возвращаемого объекта с фабрики. (Или я что-то упустил?)
Алан Кент
8

Я могу ошибаться, но это преимущество, которое я нашел.
Автоматически созданные фабрики похожи на магические добытчики или сеттеры.
Допустим, вы хотите, чтобы что-то происходило при создании экземпляра определенной сущности (назовем его BlogPost). Допустим, вы хотите установить значение по умолчанию для поля.
Пример не может быть лучшим, но выслушайте меня.
Если вы используете абстрактную фабрику, вам придется изменить ее так, чтобы при получении instanceName в качестве параметра «BlogPost» вы вызывали setDateпосле создания экземпляра.

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

Мариус
источник
Привет Marius.Спасибо за ваш ответ. Согласен с вами. Еще нужно больше информации.
Сивакумар
@sivakumar. Я хотел бы получить ответ от основного члена команды.
Мариус