Voici les réponses
pourquoi une classe proxy est utilisée dans ce cas particulier?
Si vous regardez attentivement le code ci-dessous qui est écrit pour la classe "SetConversionValueObserver", si Google Adwards n'est pas actif "retour" et s'il n'y a pas d'ordre "retour". Moyens, l'objet de collecte de commandes ne sera créé que lorsque les identifiants de commande existent et que les adwords Google sont actifs. si nous injectons la classe de collection Order réelle, le gestionnaire d'objets crée un objet de collection avec ses objets de classe parent sans savoir que Google AdWords n'est pas actif et ralentit la page de réussite de la commande. ainsi, mieux créer un objet à la demande qui est l'utilisation d'un proxy. /vendor/magento/module-google-adwords/Observer/SetConversionValueObserver.php
/**
* Set base grand total of order to registry
*
* @param \Magento\Framework\Event\Observer $observer
* @return \Magento\GoogleAdwords\Observer\SetConversionValueObserver
*/
public function execute(\Magento\Framework\Event\Observer $observer)
{
if (!($this->_helper->isGoogleAdwordsActive() && $this->_helper->isDynamicConversionValue())) {
return $this;
}
$orderIds = $observer->getEvent()->getOrderIds();
if (!$orderIds || !is_array($orderIds)) {
return $this;
}
$this->_collection->addFieldToFilter('entity_id', ['in' => $orderIds]);
$conversionValue = 0;
/** @var $order \Magento\Sales\Model\Order */
foreach ($this->_collection as $order) {
$conversionValue += $order->getBaseGrandTotal();
}
$this->_registry->register(
\Magento\GoogleAdwords\Helper\Data::CONVERSION_VALUE_REGISTRY_NAME,
$conversionValue
);
return $this;
}
quand, en général, faut-il utiliser une classe proxy?
- Injectez la classe Proxy lorsque vous pensez que la création d'objets sera coûteuse et que le constructeur de la classe est particulièrement gourmand en ressources. - lorsque vous ne voulez pas d'impact inutile sur les performances en raison de la création d'objets. - lorsque vous sentez que la création d'objet doit se produire lorsque vous appelez une méthode particulière dans une condition particulière, pas toujours. Par exemple, le constructeur de mise en page est gourmand en ressources.
Constructeur de mise en page réel vs mise en page / proxy
public function __construct(
Layout\ProcessorFactory $processorFactory,
ManagerInterface $eventManager,
Layout\Data\Structure $structure,
MessageManagerInterface $messageManager,
Design\Theme\ResolverInterface $themeResolver,
Layout\ReaderPool $readerPool,
Layout\GeneratorPool $generatorPool,
FrontendInterface $cache,
Layout\Reader\ContextFactory $readerContextFactory,
Layout\Generator\ContextFactory $generatorContextFactory,
AppState $appState,
Logger $logger,
$cacheable = true,
SerializerInterface $serializer = null
) {
$this->_elementClass = \Magento\Framework\View\Layout\Element::class;
$this->_renderingOutput = new \Magento\Framework\DataObject();
$this->serializer = $serializer ?: ObjectManager::getInstance()->get(SerializerInterface::class);
$this->_processorFactory = $processorFactory;
$this->_eventManager = $eventManager;
$this->structure = $structure;
$this->messageManager = $messageManager;
$this->themeResolver = $themeResolver;
$this->readerPool = $readerPool;
$this->generatorPool = $generatorPool;
$this->cacheable = $cacheable;
$this->cache = $cache;
$this->readerContextFactory = $readerContextFactory;
$this->generatorContextFactory = $generatorContextFactory;
$this->appState = $appState;
$this->logger = $logger;
}
Constructeur proxy, jetez un oeil, aucun constructeur parent appelé ainsi que le nom de classe de disposition juste passé afin que la création d'objet réelle se produise lors de l'appel de la méthode.
/**
* Proxy constructor
*
* @param \Magento\Framework\ObjectManagerInterface $objectManager
* @param string $instanceName
* @param bool $shared
*/
public function __construct(
\Magento\Framework\ObjectManagerInterface $objectManager,
$instanceName = \Magento\Framework\View\Layout::class,
$shared = true
) {
$this->_objectManager = $objectManager;
$this->_instanceName = $instanceName;
$this->_isShared = $shared;
}
La classe proxy a une méthode pour créer un objet à la demande, _subject est l'objet de la classe passée.
/**
* Get proxied instance
*
* @return \Magento\Framework\View\Layout
*/
protected function _getSubject()
{
if (!$this->_subject) {
$this->_subject = true === $this->_isShared
? $this->_objectManager->get($this->_instanceName)
: $this->_objectManager->create($this->_instanceName);
}
return $this->_subject;
}
Et la méthode appelée using _subject.
/**
* {@inheritdoc}
*/
public function setGeneratorPool(\Magento\Framework\View\Layout\GeneratorPool $generatorPool)
{
return $this->_getSubject()->setGeneratorPool($generatorPool);
}