Warning: file_get_contents(/data/phpspider/zhask/data//catemap/8/variables/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Php Magento-在控制器和块之间传递数据_Php_Variables_Magento_Model_Session Variables - Fatal编程技术网

Php 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')

这个问题非常简单快捷,但我找不到一个合适的答案——在Magento中将数据从控制器传递到块的最佳方式是什么

如果有不同,我将按如下方式加载布局:

 $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')

  • 使用magic getter/setter在模型上设置值(从
    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