How to get the identifiers of the categories in which the product is located, in relation to the store in which I am now

I am on the product page and have a product object, but when I try to get category identifiers using:

$_product->getCategoryIds(); 

or

 $_product->getResource()->getAttribute('category_ids')->getFrontend()->getValue($_product); 

he gets all the category identifiers, and I just want them in the store I am in.

This is a multi-user environment, hence my problem. Everything else looks fine, and the category list works fine. This is my only problem. Can anyone help?

+4
source share
3 answers

Pretty similar to Alans answer, maybe a little less cycles:

 $rootCategory = Mage::getModel('catalog/category') ->load(Mage::app()->getStore()->getRootCategoryId()); $sameStoreCategories = Mage::getResourceModel('catalog/category_collection') ->addIdFilter($product->getCategoryIds()) ->addFieldToFilter('path', array('like' => $rootCategory->getPath() . '/%')) ->getItems(); var_dump(array_keys($sameStoreCategories)); 

It will always work. It's ugly that you still need to load categories.

Here is an option you can use if tables with a flat category are included:

 $sameStoreCategories = Mage::getResourceModel('catalog/category_flat_collection') ->addIdFilter($product->getCategoryIds()) ->getItems(); var_dump(array_keys($sameStoreCategories)); 

Why does it work? Because flat tables are indexed by the repository, and each flat table contains only entries for category entities that are associated with this category of store category roots.

So, despite the fact that you filter all category identifiers associated with the product, the collection will only contain categories that are present in the current store.

+10
source

if you have millions of categories or millions of products or you need a collection of all products with all their categories - you can try the following ugly method (again, it works only after regrouping flat indexes):

  • in some installers or cron - create a new table and keep it up to date with the following query

for each repository:

 CREATE TABLE IF NOT EXISTS categories_X SELECT product_id, CONVERT(GROUP_CONCAT(category_id) USING utf8) as category_id FROM catalog_category_product where category_id in (select entity_id from catalog_category_flat_store_X) GROUP BY product_id 
  • where X is the store identifier

  • write the model again or direct request to get all categories for the desired store and product

+1
source

This is a bit complicated, so if the following does not work, it is probably code, not you.

The problem is, as far as I can tell, Magento does not keep track of which categories are in the store. Instead, Magento tracks the root category for a specific repository.

This means that when we have a list of category identifiers, we need to grab the root category for each, and then check whether this root category matches the root category of the current store.

The following code should do it, but please check this with various products

  //get root category for current store $store_root_id = Mage::app()->getStore()->getRootCategoryId(); //get category IDs from product $ids = $product->getCategoryIds(); //load full cateogires $categories = Mage::getModel('catalog/category') ->getCollection() ->addIdFilter($ids); //filter out categories with different root $category_ids = array(); foreach($categories as $cat) { //path property is 1/root_id/id/id $parts = explode('/', $cat->getPath()); $one = array_shift($parts); $root_id = array_shift($parts); if($root_id == $store_root_id) { $category_ids[] = $cat->getId(); } } var_dump($category_ids); 
0
source

All Articles