Php Magento-在控制器和块之间传递数据
这个问题非常简单快捷,但我找不到一个合适的答案——在Magento中将数据从控制器传递到块的最佳方式是什么 如果有不同,我将按如下方式加载布局:Php Magento-在控制器和块之间传递数据,php,variables,magento,model,session-variables,Php,Variables,Magento,Model,Session Variables,这个问题非常简单快捷,但我找不到一个合适的答案——在Magento中将数据从控制器传递到块的最佳方式是什么 如果有不同,我将按如下方式加载布局: $this->loadLayout(array('default', 'myModule_default')); $this->_initLayoutMessages('customer/session') ->_initLayoutMessages('catalog/session')
$this->loadLayout(array('default', 'myModule_default'));
$this->_initLayoutMessages('customer/session')
->_initLayoutMessages('catalog/session')
->renderLayout();
我要补充一点,我使用注册表的方式如下:
$this->loadLayout(array('default', 'myModule_default'));
$this->_initLayoutMessages('customer/session')
->_initLayoutMessages('catalog/session')
->renderLayout();
在控制器中:
Mage::register('data', $data);
在区块中:
$data = Mage::registry('data');
但不确定这是否是最好的方法。使用
Mage::registry()
方法,您的思路是正确的。另一个选项是使用自动getter和setter,例如在控制器中使用$this->setRandomVariableName($data)
,然后在块中使用$this->getRandomVariableName()
。我没有调查它们是否在堆栈中的相同位置结束(我假设在会话中它们是特定于请求的),但它们在代码中实现了相同的目标
使用getter和setter有时会让人困惑,因为它看起来像是通过ORM而不是“临时”会话变量访问数据,因此您可能会做出编码风格一致性决策,对这些类型的变量使用
Mage::registry
。您的选择是真的。在中对我起作用的是通过执行以下操作在控制器中设置变量:
Mage::register('variable', 'value');
然后在视图中,使用以下代码检索值:
$variable = $this->getVariable();
你没有
在Magento的MVC方法中,控制器不负责为视图设置变量(在Magento的情况下,视图是布局和块)。控制器设置模型上的值,然后阻止从这些模型读取数据。在Magento的世界观中,依赖控制器执行特定操作的块是紧密耦合的,应该避免
控制器的工作是对模型执行某些操作,然后告诉系统它的布局渲染时间。就这样。根据系统模型的状态,以某种方式显示HTML页面是布局/块的工作
所以,如果我想模仿传统的PHP MVC行为,我会
Varien\u对象继承的简单模型类
Mage::getSingleton('foo/bar')
Varien_Object
继承的对象中获取这些值),或setData
等Mage::getSingleton('foo/bar')
再次实例化模型,并读回值当您使用
Mage::getSingleton(…)实例化模型时,
Magento将对象实例化为一个singleton。因此,如果您重新实例化一个对象(再次使用Mage::getSingleton('foo/bar')
),您将得到相同的对象 如果您使用的块继承了Mage\u Core\u Block\u模板
(即使用模板来显示),则可以使用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中并不经常使用,但由于它是作为公共方法实现的,因此被声明为稳定的,所以我认为这样做很好。
这也是约定以下划线(例如,$\u product=$this->getProduct()
)开始在模板中声明变量的原因,以便可以将它们与指定的变量区分开来。您可以对某些值使用setData/getData对。
我在controller中使用setData,在block中使用getData。@Draw在JavaServer Faces中使用了一些背景,在PHP/Magento中使用了一些新的背景,我想声明
“‘不共享’PHP架构”
请参阅,这会导致PHP中的所有对象(甚至类)都具有作用域“request”
如果我得到了艾伦的观点,他建议使用
- 一个“有状态”模型对象,其属性中包含一些不一定存储在数据库中的数据
- 以及singleton模式,通过使用Mage::getSingleton,使这个在控制器中实例化的有状态模型可以访问块,从而可以访问呈现输出的实际模板
由于像这样的工具减少了创建新模型的时间,这似乎真的很有意义。我以前尝试过这一点,假设会有神奇的getter和setter-但我总是会遇到一个未定义的方法错误。嗯,也许你需要一个实例化的模型来执行自动神奇的get/set。在控制器上下文中,它可能无法处理$this。如果您的控制器已经有一个由“Mage::getModel('module/model')创建的对象,那么您应该能够使用它。它可能还为变量提供了更多的上下文,这是一件好事…Magic getPropName和setPropName仅适用于从Varien_对象继承的对象。@Alan谢谢,这很有意义。您是否会说,在某些情况下,拥有一个模型会增加更多不必要的复杂性,并且使用前面描述的注册表就足够了。或者,你会一直主张坚持这种模式,并始终对任何数据使用模型吗?这是我很难有太多意见的任意事情之一。我认为注册表类似于全局变量,“如果没有其他方法,那是最后的选择”。两件随机的事情要考虑“如果在未设置注册表变量的上下文中使用视图/块,会发生什么情况。其次,值得注意的是,目前,Magnetor的getSingleton是通过将初始对象实例化缓存到注册表来实现的。所以我坚持使用模型方法,因为我有一个更大的理念“像核心团队那样做事”。谢谢,这消除了我对标准Zend MVC应用程序的困惑。@Neil Yeah