I had some issues with the Menu Token module, so I looked into an alternative. I found that there is an easy way to add dynamic components in menu links. Let's say that you are creating a webshop with Drupal Commerce and that you want to create a link to the user's orders. The link would have to look something like this:
/user/{{ currentUserID }}/orders
As you can probably guess, {{ currentUserID }} is a dynamic component. Each user has a different ID. You can create such a link by creating two files inside your custom module.
First, you need to create a my_module.links.menu.yml file in the root directory of your module:
my_module.user_orders:
weight: -50
menu_name: account
class: Drupal\my_module\Plugin\Menu\UserOrdersMenuLink
As you can see this link will appear in the User account menu. The link path is generated in the UserOrdersMenuLink class. Let's see how that class looks like:
<?php
namespace Drupal\my_module\Plugin\Menu;
use Drupal\Core\Menu\MenuLinkDefault;
use Drupal\Core\Menu\StaticMenuLinkOverridesInterface;
use Drupal\Core\Session\AccountInterface;
use Drupal\Core\Url;
use Symfony\Component\DependencyInjection\ContainerInterface;
class UserOrdersMenuLink extends MenuLinkDefault {
protected $currentUser;
public function __construct(array $configuration, $plugin_id, $plugin_definition, StaticMenuLinkOverridesInterface $static_override, AccountInterface $current_user) {
parent::__construct($configuration, $plugin_id, $plugin_definition, $static_override);
$this->currentUser = $current_user;
}
public static function create(ContainerInterface $container, array $configuration, $plugin_id, $plugin_definition) {
return new static(
$configuration,
$plugin_id,
$plugin_definition,
$container->get('menu_link.static.overrides'),
$container->get('current_user')
);
}
public function getTitle() {
return $this->t('My Orders');
}
public function getUrlObject($title_attribute = TRUE) {
return Url::fromUri('internal:/user/' . $this->currentUser->id() . '/orders');
}
}
And that's it. Clear the cache and go to the user menu: Structure -> Menus -> User account menu. You should see your new dynamic link there.
Please note that Drupal 8 adheres to PSR-4. This means that files must be named in certain ways and placed in specific folders. Here is what the module structure should look like:
my_module
├── my_module.info.yml
├── my_module.links.menu.yml
└── src
└── Plugin
└── Menu
└── UserOrdersMenuLink.php
About the Author
Goran Nikolovski is a senior web developer who loves working with Drupal, React, and React Native. He is the founder of this website and he enjoys sharing his knowledge. Need help with anything? Get in touch.