Receiving error but not sure what it is
-
13-12-2019 - |
Question
I am writing a custom function which gives me cross sell items from products from cart.
I have wrote this function as follow:
$quote = $this->getQuote();
$quoteItems = $quote->getAllItems();
$productIds = array();
foreach($quoteItems as $item){
if (!$item->getParentItem()) {
$product = Mage::getModel('catalog/product')->load($item->getProductId());
$productIds[] = $product->getCrossSellProductIds();
}
}
if ($productIds) {
$productCollection = Mage::getModel('catalog/product')
->getCollection()
->setStoreId($this->getQuote()->getStoreId())
->addStoreFilter($this->getQuote()->getStoreId())
->addAttributeToSelect('name')
->addAttributeToSelect('price')
->addAttributeToSelect('small_image')
->addIdFilter($productIds)
->load();
}
}
return $productCollection;
But this gives me error for some few products only. Not sure what's going on.
As I understand it is trying to filter products from store
.
Error
a:5:{i:0;s:238:"SELECT
e
.* FROMcatalog_product_entity
ASe
INNER JOINcatalog_product_website
ASproduct_website
ON product_website.product_id = e.entity_id AND product_website.website_id = '1' WHERE (e
.entity_id
IN('46', '56', '60', ))
Can anyone point me out what's happening, since magento is not giving me specific reason for the error.
Solution
Seems like from your error message could be reason of addIdFilter
you can try
passing a string with comma separated ids:
->addIdFilter("46, 56, 60") // instead of IN('46', '56', '60', )) extra comma :(
If that does not work you can always try:
->addAttributeToFilter('entity_id', array('in' => array(46, 56, 60)))
hope this will work for you.
OTHER TIPS
WHERE (e.entity_id IN('46', '56', '60', ))
there's a trailing comma there.
Where you're calling $productIds[] = $product->getCrossSellProductIds()
in a loop, you're ending up with an array that probably looks something like
$productIds = array(array('46', '56', '60'), array())
I don't want to go down the rabbit hole of what happens after you call addIdFilter
, but I would imagine that it's not expecting an array of arrays with empty arrays, hence the bad sql generation.
If I were you I would check what $productIds looks like before you add it to the collection, and if it isn't a flat collection of product ids I would flatten it down so it was and see if that fixed it.
You must ensure to define $productsCollection outside the if statement so if your product has not crosssells products related you will return an undefined var.
It looks strange the double "store" and "storeId" filter applied, with addStoreFilter() would reach.
I suggest to get the crosssells ids directly from the database in order to get a better performance, you can get all these ids with a lightweight query, avoiding re-load every product in quote. Finally, isn't an attribute "id" to filter, you should use "entity_id" instead.
Alright, I have accepted liyakat 's answer, however it's not complete. So I have also added answer here.
After looking to all given answer, @liyakat pointed me to right direction, but not giving me the solution, since I am not running custom query there.
Here is my answer:
$quote = $this->getQuote();
$quoteItems = $quote->getAllItems();
$productIds = array();
foreach($quoteItems as $item){
if (!$item->getParentItem()) {
$product = Mage::getModel('catalog/product')->load($item->getProductId());
//putting to if condition so if there is no cross sell for the item then it will not load up.
// and this will remove that empty node at the end.
if(count($product->getCrossSellProductIds()) > 0){
$productIds[] = $product->getCrossSellProductIds();
}
}
}
if ($productIds) {
$productCollection = Mage::getModel('catalog/product')
->getCollection()
->setStoreId($this->getQuote()->getStoreId())
->addStoreFilter($this->getQuote()->getStoreId())
->addAttributeToSelect('name')
->addAttributeToSelect('price')
->addAttributeToSelect('small_image')
->addIdFilter($productIds)
->load();
}
}
return $productCollection;
Hope this will help others in future.