I am building a module which already has the function Mymodule_menu() at the beginning of the code. I was wondering if it is possible to use hook_menu_alter() to add new menu items (i.e. building new pages) somewhere down the code.

What I'm trying to do is build a form module whereas when the user presses "Submit", the code inside the form_submit() function will build a new page using the form values the user entered, and then redirects the user to that page.

Is that even possible. Appreciate the help from anyone. Thank you all in advance!

  • You can add new menu items to hook_menu() at any time, but they won't become available until you clear the cache.
    – Jaypan
    Nov 27, 2016 at 12:32

3 Answers 3


No, hook_menu_alter() is not thought to dynamically add new routes. As any similar alter hook, it is thought to alter the routes defined from other modules.
It would not work for dynamically adding new routes for the simply fact that, similarly to hook_menu() is only invoked in specific cases, for example, when a module is installed, uninstalled, enabled, or disabled.

If you need to have dynamic pages, you need to do what Drupal does for nodes: You define a route with wildcards, which is similar to the node/%node route defined for nodes.
hook_menu() has some example for this kind of routes, under Wildcards in Paths.

For example, a route definition as the following could be used to serve a page like my-module/1, my-module-2, etc. mymodule_abc() would recive the wildcard value as argument, and it could use that argument to access data from a database table, which is essentially what Drupal does when a user visits node/1: It loads the node whose ID is equal to 1 from the node table, and it shows it to the user who requested that page.

  $items['my-module/%'] = array(
    'page callback' => 'mymodule_abc',
    'page arguments' => array(1),

As side note, as said in Auto-Loader Wildcards, instead of my-module/%, you could use my-module/%mymodule_abc, and mymodule_abc_load() will be called every time a page like my-module/1 is accessed, getting the wildcard value (1) as argument; it could then return the object saved in the database from the form submission handler.
See node_load() as example. That function returns the object saved in the database from the form submission handler of the node edit form.

Auto-Loader wildcards are helpful when there are more routes that your module defines. For example, the Node module uses them because the routes it defines using wildcards are node/%node, node/%node/edit, and node/%node/delete. Instead of putting the code to load the node in 3 different page callbacks, it puts the code in a single function (node_load()) automatically called from Drupal.


From your question it seems, you're trying to add new menu entry in custom module where we should be using hook_menu. The only thing to avoid is adding new menu entry in Core or Contributed module(s). hook_menu_alter is used in custom module to alter existing menu item defined by Core or Contributed modules.

Below is descripton taken from hook_menu API page.

Define menu items and page callbacks.

Below is descripton taken from hook_menu_alter API page.

Alter the data being saved to the {menu_router} table after hook_menu is invoked.


I also found the thread "Sending results of form to new page" which was talking about exactly what I need.


Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.