WooCommerce Tips & Tricks – Get all the categories to which a product belongs
As active contributors of several communities, such as the Advanced WooCommerce and WooCommerce Help & Share groups on Facebook, we came across a question that seem to be quite frequent.
How to get all of a product’s categories
This operation is simple, it just requires a bit more work than one would expect. It’s very easy to fetch the categories to which a product is assigned directly, but a product may also belong to parent categories (a parent category is a category to which a subcategory belongs). The screenshot below explains the concept.
In the above example, the product belongs to the following categories:
- Directly to Subcategory A1 and Some other category, as it’s assigned directly to them.
- Indirectly to Category A, which is the parent of Subcategory A1.
Now that the concepts are clear, let’s get coding.
Step 1 – Get the direct categories of a product
This is the easiest part. It’s just a matter to find all the “category” terms associated to a product. Our function will look like this:
function aelia_get_product_categories($product, $return_raw_categories = false) { $result = array(); // Get all the categories to which a product is assigned $categories = wp_get_post_terms($product->id, 'product_cat'); // The $categories array contains a list of objects. Most likely, we would // like to have categorys slug as a keys, and their names as values. The# // wp_list_pluck() function is perfect for this $categories = wp_list_pluck($categories, 'name', 'slug'); return $categories; }
The result of this function, once applied to our example product, will be the following:
array( 'subcategory-a1' => 'Subcategory A1', 'some-other-category' => 'Some other category', )
All good, we have the categories to which the product is assigned directly. Now we need to get all the parent categories.
Step 2 – Get the parent category (or categories) of a given category
To keep things tidy, we will create a second function to get the parent categories of a category. This requires a similar approach to the one used for the products.
function aelia_get_parent_categories($category_id) { $parent_categories = array(); // This will retrieve the IDs of all the parent categories // of a category, all the way to the top level $parent_categories_ids = get_ancestors($category_id, 'product_cat'); foreach($parent_categories_ids as $category_id) { // Now we retrieve the details of each category, using its // ID, and extract its name $category = get_term_by('id', $category_id, 'product_cat'); $parent_categories[$category->slug] = $category->name; } return $parent_categories; }
The above will return the following result for Subcategory A1:
array( 'category-a' => 'Category A' )
As before, we have a list with category slugs as keys, and category names as values. Time to finish the job.
Step 3 – Putting the pieces together
Now that we can get both the direct categories of a product and their parent categories, we can alter the first function to call the second and give us a result that includes all the categories. The modified function will look as follows:
function aelia_get_product_categories($product, $return_raw_categories = false) { $result = array(); $categories = wp_get_post_terms($product->id, 'product_cat'); if(is_array($categories) && !$return_raw_categories) { $parent_categories = array(); // Retrieve the parent categories of each category to which // the product is assigned directly foreach($categories as $category) { // Using array_merge(), we keep a list of parent categories // that doesn't include duplicates $parent_categories = array_merge($parent_categories, aelia_get_parent_categories($category->term_id)); } // When we have the full list of parent categories, we can merge it with // the list of the product's direct categories, producing a single list $categories = array_merge($parent_categories, wp_list_pluck($categories, 'name', 'slug')); } return $categories; }
As you will probably have guessed, the new function will return the following result:
array( 'subcategory-a1' => 'Subcategory A1', 'some-other-category' => 'Some other category', 'category-a' => 'Category A', )
That is, a list of all the direct and indirect categories to which a product belongs. Mission accomplished!
For your convenience, you can find the complete code here: WooCommerce – WooCommerce – Get product categories, including parent categories (Pastebin).
Need help?
Should you need help implementing the solution, or if you would need to have the category search functions implemented as part of a more complex custom project, please feel free to contact us. We will review your specifications and give you a quote for your customisation.
The Aelia Team