Magento 1.7中的重新排序/侧边栏显示了不可见的产品-在早期版本中工作


Reorder/Sidebar in Magento 1.7 shows invisible products - works in earlier versions

我有一个虚拟产品的插件,设置为VISIBILITY_NOT_VISIBLE。这是一个虚拟产品。

然而,它显示在小部件"我的订单"-但仅在Magento 1.7。它在1.6和1.5中运行良好。我在getItems()方法中测试了Mage/Sales/Block/Reorder/Sidebar.php,它确实具有正确的VISIBILITY_NOT_VISIBLE状态。

  1. 在这方面magento 1.6到1.7之间有什么变化吗?我可以发现代码库中的差异,但不是导致这种行为的原因。

  2. 这可能是一个bug,因为它只出现在1.7?

  3. 我可以绕过这个不触及原始代码库?

你是正确的。我不确定这是否是一个bug(但作为功能方面,这应该是一个bug)。

所以1.6(和旧版本)/和1.7之间的区别是:

The Model

Mage_Sales_Model_Order

有这个方法

protected function _getItemsRandomCollection($limit, $nonChildrenOnly = false){  
        $(...)->setVisibility(Mage::getSingleton('catalog/product_visibility')->getVisibleInSiteIds()) // This is Visibility check ( its fine ) 
            foreach ($collection as $item) {
                $product = $productsCollection->getItemById($item->getProductId());
                if ($product) {
                    $item->setProduct($product); // Set Object Data ( 'product' ) if it exists 
                }
            }
}

因此,在前面的代码中,最后一个订购的商品集合有一个名为"product"的属性,如果返回则保存product对象,如果未返回则不设置。

上面的代码很好,没有问题。

In Model

Mage_Sales_Block_Reorder_Sidebar

getiitems方法是:

/**
 * Get list of last ordered products
 *
 * @return array
 */
public function getItems()
{
    $items = array();
    $order = $this->getLastOrder();
    $limit = 5;
    if ($order) {
        $website = Mage::app()->getStore()->getWebsiteId();
        foreach ($order->getParentItemsRandomCollection($limit) as $item) {
            if ($item->getProduct() && in_array($website, $item->getProduct()->getWebsiteIds())) {
                $items[] = $item;
            }
        }
    }
    return $items;
}

================================================================================= Magento 1.6及之前版本

当你在侧边栏中调用$item->getProduct();

它将返回在上面的方法(_getItemsRandomCollection())中设置的对象属性(Mage_Catalog_Model_Product -产品实例-)

如果没有设置,则返回NULL。

如果它返回Product对象这个项目将显示在侧边栏块中如果没有返回数组将不包含Virtual item

=================================================================================

当你在侧边栏中调用$item->getProduct();

===>> 此方法在模型

中实现

Mage_Sales_Model_Order_Item

当你调用该方法时,它将从模型中执行(它不会查找对象属性)。

如果你看一下方法实现

/**
 * Retrieve product
 *
 * @return Mage_Catalog_Model_Product
 */
public function getProduct()
{
    if (!$this->getData('product')) { // If no object attribute set with name ('product')
        $product = Mage::getModel('catalog/product')->load($this->getProductId()); // it will always return product instance with that product id.
        $this->setProduct($product); // set it to the current sidebar item
    }
    return $this->getData('product'); // return the object property 'product'
}

所以在这种情况下,如果方法(_getItemsRandomCollection())没有设置对象属性'product',因为它不可见或其他(这个方法将通过产品ID直接分配它,而不检查可见性或其他任何东西。

是的,我认为这是一个bug,需要修复

这就是为什么

=================================================================================

解决方法很简单

1。创建自定义模块

2。扩展/重写模型

Mage_Sales_Model_Order_Item

3。重写方法和(注释代码块)或在方法中添加可见性检查。

解决方案1(注释设置项目product的代码块)

/**
 * Retrieve product
 *
 * @return Mage_Catalog_Model_Product
 */
public function getProduct()
{
    /** comment from here 
    *if (!$this->getData('product')) {
    *    $product = Mage::getModel('catalog/product')->load($this->getProductId());
    *    $this->setProduct($product);
    *}
    * Till here.
    */
    return $this->getData('product');
}

解决方案2:如下所示在方法中添加可见性检查。

/**
 * Retrieve product
 *
 * @return Mage_Catalog_Model_Product
 */
public function getProduct()
{
    if (!$this->getData('product')) {
        $product = Mage::getModel('catalog/product')->load($this->getProductId());
        if(!$product->isVisibleInSiteVisibility()) // add visibility check here
        {
             $this->setProduct($product);
        }
    }
    return $this->getData('product');
}

我花了一些时间来做这个:)希望它对你有帮助!