cancel
Showing results for 
Search instead for 
Did you mean: 

Magento product URL with and without category

Magento product URL with and without category

I have removed the category from the product URL by overriding getUrlPath method in CategoryUrlPathGenerator using a module and is working fine. But now I need to show the product page on both with and without category in URL. Is there a way I could achieve this? Below is the code in getUrlPath.
public function getUrlPath($category, $parentCategory = null)
    {
        if (in_array($category->getParentId(), [Category::ROOT_CATEGORY_ID, Category::TREE_ROOT_ID])) {
            return '';
        }
        $path = $category->getUrlPath();
        if ($path !== null && !$category->dataHasChangedFor('url_key') && !$category->dataHasChangedFor('parent_id')) {
            return $path;
        }
        $path = $category->getUrlKey();
        if ($path === false) {
            return $category->getUrlPath();
        }

        return $path;
    }
1 REPLY 1

Re: Magento product URL with and without category

Here's an example of how you can do it

First, create a custom module in your Magento installation. Let's assume the module's name is Vendor_ Module.


Then go to in your module's etc directory, create a di.xml file and add the following content to override the ProductUrl class

<?xml version="1.0"?>
<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="urn:magento:framework:ObjectManager/etc/config.xsd">
    <preference for="Magento\Catalog\Model\Product\Url" type="Vendor\Module\Model\Product\Url" />
</config>

Now, create the Url.php file inside Vendor/Module/Model/Product directory with the following content.

<?php
namespace Vendor\Module\Model\Product;

use Magento\Catalog\Model\Product;

class Url extends \Magento\Catalog\Model\Product\Url
{
    /**
     * Retrieve product URL
     *
     * @param \Magento\Catalog\Model\Product $product
     * @param array $params
     * @return string
     */
    public function getUrl($product, $params = [])
    {
        // Get the current category if exists
        $category = $this->_registry->registry('current_category');

        // Check if the category exists and the product is assigned to it
        if ($category && $product->getCategoryIds() && in_array($category->getId(), $product->getCategoryIds())) {
            // If the product is assigned to the current category, include the category path in the URL
            return $this->getUrlPath($product, $category) . $this->getUrlSuffix($product);
        }

        // If not assigned to the current category, generate the URL without the category path
        return parent::getUrl($product, $params);
    }
}

I hope this example will help you.