In this guide, you will learn how to add a custom admin menu and an admin controller in Magento 2.
We will cover all steps from configuration to routing and controller implementation.
If you want to learn how to create a module, you can check our blog Create a Module in Magento2
Overview of Admin Menu and Controller
Magento 2 uses XML configuration files to define admin menus and URL routing.
An admin controller processes backend requests and renders the proper admin page.
Step 1: Create the Admin Route
Every admin controller needs a route file.
Create routes.xml under etc/adminhtml/ in your module folder.
Here’s how the file structure should look:
app/code/Vendor/Module/etc/adminhtml/routes.xml
Use this XML to register your admin route:
<?xml version="1.0"?>
<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:noNamespaceSchemaLocation="urn:magento:framework:App/etc/routes.xsd">
<router id="admin">
<route id="vendor_module" frontName="vendor_module">
<module name="Vendor_Module" />
</route>
</router>
</config>
This tells Magento 2 to recognize backend URLs under vendor_module/*.
Step 2: Define the Admin Menu
You must create a menu item to access your admin controller.
Create menu.xml inside etc/adminhtml/.
Add this basic structure to register your menu:
<?xml version="1.0"?>
<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:noNamespaceSchemaLocation="urn:magento:module:Magento_Backend:etc/menu.xsd">
<menu>
<add id="Vendor_Module::main"
title="My Module"
module="Vendor_Module"
sortOrder="10"
resource="Vendor_Module::main"/>
<add id="Vendor_Module::subitem"
title="Manage Items"
module="Vendor_Module"
sortOrder="20"
parent="Vendor_Module::main"
action="vendor_module/manage/index"
resource="Vendor_Module::subitem"/>
</menu>
</config>
This configuration generates a parent menu My Module and a child Manage Items.
idis a unique identifier.titlelabels the menu item.parentnests the child under the parent item.actiondefines the controller path to load.
Step 3: Create the Admin Controller
Controllers handle the logic when a menu item is clicked.
Create a new folder Controller/Adminhtml/Manage under your module root.
Now add the file Index.php with this structure:
<?php
namespace Vendor\Module\Controller\Adminhtml\Manage;
use Magento\Backend\App\Action;
use Magento\Backend\App\Action\Context;
use Magento\Framework\View\Result\PageFactory;
class Index extends Action
{
protected $resultPageFactory;
public function __construct(
Context $context,
PageFactory $resultPageFactory
) {
parent::__construct($context);
$this->resultPageFactory = $resultPageFactory;
}
public function execute()
{
$resultPage = $this->resultPageFactory->create();
$resultPage->setActiveMenu('Vendor_Module::subitem');
$resultPage->getConfig()->getTitle()->prepend(__('Manage Items'));
return $resultPage;
}
protected function _isAllowed()
{
return $this->_authorization->isAllowed('Vendor_Module::subitem');
}
}
This controller renders the admin page when you click your menu.
execute()loads a page layout and title.setActiveMenu()highlights your menu item._isAllowed()ensures proper permissions.
Clear Cache and Test
After creating files, run the following:
- php bin/magento cache:flush
Refresh your admin panel to see the new menu. Clicking it should load your admin page.
Conclusion
You learned how to:
- Register a backend route.
- Create an admin menu item.
- Build a controller to render content.
By following this structure, you can add powerful admin functionality to any Magento 2 module.
You can also Download sample code form github

5 comments