Magento - Передача данных между контроллером и блоком


Действительно быстрый и простой вопрос, но я не могу найти достойного ответа на этот вопрос - Как лучше всего передавать данные с контроллера в блок в Magento.

Если это имеет значение, я загружаю макет следующим образом:

 $this->loadLayout(array('default', 'myModule_default'));

    $this->_initLayoutMessages('customer/session')
         ->_initLayoutMessages('catalog/session')
         ->renderLayout();

Я должен добавить, что я использую реестр следующим образом:

В контроллере:

Mage::register('data', $data);

В блоке:

$data = Mage::registry('data');

Хотя не уверен, что это лучший способ сделать это.

Author: Jonathan Day, 2010-10-24

6 answers

Ты этого не делаешь.

В подходе MVC Magento контроллер не несет ответственности за установку переменных для представления (в случае Magento представление - это макет и блоки). Контроллеры устанавливают значения для моделей, а затем блокируют чтение из тех же моделей. С точки зрения Magento, наличие блока, зависящего от контроллера, выполняющего определенную задачу, является тесной связью, и его следует избегать.

Задача вашего контроллера состоит в том, чтобы делать определенные вещи с моделями, а затем сообщать система это время отрисовки макета. Вот и все. Это ваша задача макета/блоков отображать HTML-страницу определенным образом в зависимости от состояния моделей системы.

Итак, если бы я хотел эмулировать традиционное поведение PHP MVC, я бы

  1. Создайте простой класс модели, наследуемый от Varien_Object

  2. В контроллере создайте экземпляр этого объекта, используя Mage::getSingleton('foo/bar')

  3. Установите значения в модели, используя магический геттер/сеттеры (вы получаете их в объектах которые наследуются от Varien_Object) или setData и т. Д.

  4. В блоках снова создайте экземпляр модели с помощью Mage::getSingleton('foo/bar') и считайте значения обратно.

При создании экземпляра модели с помощью Mage::getSingleton(...) Magento создаст экземпляр объекта как одноэлементный . Итак, если вы повторно создадите экземпляр объекта (снова с помощью Mage::getSingleton('foo/bar')), вы получите тот же объект.

 81
Author: Alan Storm, 2010-10-24 02:10:51

Если вы используете блоки, которые наследуют Mage_Core_Block_Template ( т. е. которые используют шаблон для отображения) вы можете назначить данные с помощью метода assign(), как только блоки будут созданы с помощью loadLayout()

$this->loadLayout(array('default', 'myModule_default'));

$this->getLayout()->getBlock('your.block.name.in.the.layout')->assign('data', $data);

Затем в шаблоне .phtml вы можете просто использовать

<?php echo $data ?>

Это не очень часто используется в magento, но поскольку оно реализовано как общедоступные методы и, следовательно, объявлено стабильным, я считаю, что это нормально. Это также является причиной для того, чтобы конвенция начинайте переменные, объявленные в шаблоне с подчеркиванием (например, $_product = $this->getProduct()), чтобы их можно было отличить от назначенных переменных.

 35
Author: Vinai, 2016-02-02 14:11:47

Что сработало для меня в том, чтобы установить переменную в контроллере, выполнив:

Mage::register('variable', 'value');

А затем в представлении вы получите значение, используя следующий код:

$variable = $this->getVariable();
 4
Author: Josh Pennington, 2010-10-23 23:51:59

Вы на правильном пути, используя подход Mage::registry(). Другой вариант - использовать автоматические геттеры и сеттеры, например, $this->setRandomVariableName($data) в контроллере, а затем в блоке использовать $this->getRandomVariableName(). Я не исследовал, оказываются ли они в одном и том же месте в стеке (я предполагаю, что в сеансе, поскольку они зависят от запроса), но они достигают той же цели в коде.

Использование геттеров и сеттеров иногда может привести к путанице, так как может показаться, что вы получаете доступ к данным через ORM вместо "временной" переменной сеанса, поэтому вы можете принять решение о согласованности в стиле кодирования, чтобы использовать Mage::registry для этих типов переменных. На самом деле это ваш выбор.

 2
Author: Jonathan Day, 2010-10-23 22:22:17

Для некоторых значений можно использовать пару setData/getData. Я использовал setData в контроллере и getData в блоке.

 0
Author: Taras, 2011-07-12 09:04:24

@Нарисовал С некоторым фоном в JavaServer Faces и довольно новым в PHP/Magento, я хотел бы заявить, что

"архитектура PHP "ничего общего"",

Смотрите PHP не является Java: Технический документ по управлению сеансами", приводит к тому, что все объекты (и даже классы) в PHP имеют область "запрос".

Если у меня есть точка Алана, то он советует использовать

  • объект модели с отслеживанием состояния, в атрибутах которого есть некоторые данные, которые не обязательно хранится в базе данных
  • и шаблон одноэлементного, с помощью Mage::getSingleton, чтобы сделать эту модель с отслеживанием состояния, которая создается в контроллере, доступной для блока и, следовательно, в фактическом шаблоне, который отображает выходные данные.

И поскольку такой инструмент, как MTOOL, сокращает время на создание новой модели, это действительно имеет смысл.

 0
Author: paderEpiktet, 2011-08-05 12:52:43