9

I am developing a module, but the hooks I am adding are not invoked from Drupal. It happens with more than one hook.

I read the documentation for the hooks, and I cannot find anything that would explain why this happens. I verified I am using the correct parameters, and returning the correct value.

What am I doing wrong? Is there anything I am missing?

  • This question is thought as canonical question for those questions about hooks not being invoked by Drupal. – kiamlaluno Jan 14 '13 at 16:28
13

When developing a module, you should keep in mind the following notes.

  • The implementation of a hook done from a module is a function whose name is prefixed with the module short name (also called the machine name); from the hook name, take off the hook part, and replace it with the module machine name. For example, the implementation of hook_menu() done from example.module is example_menu(). If the module is example_menu.module, and the function is example_menu(), that is not considered the hook_menu() implementation for example_menu.module.
    This also means, for example, that the hook_form_alter() implementation in example_form.module is not example_form_alter(), but example_form_form_alter(). As another example, the implementation of hook_form_FORM_ID_alter() done for altering the form returned from user_register_form() from example.module is not example_form_user_register_alter(), but example_form_user_register_form_alter(). (The form ID is user_register_form.)

  • Generally speaking, using uppercase characters in the module machine name doesn't create problems: PHP doesn't make differences between myModule_get_value(), and mymodule_get_value(), and $value = myModule_get_value() would call either myModule_get_value(), or mymodule_get_value().
    Although, there is a case where using upper case characters in a module machine name would cause problems: when defining the update hooks for a module. drupal_get_schema_versions(), the function that returns a list of available updates, contains the following code.

    // Prepare regular expression to match all possible defined hook_update_N().
    $regexp = '/^(?P<module>.+)_update_(?P<version>\d+)$/';
    $functions = get_defined_functions();
    // Narrow this down to functions ending with an integer, since all
    // hook_update_N() functions end this way, and there are other
    // possible functions which match '_update_'. We use preg_grep() here
    // instead of foreaching through all defined functions, since the loop
    // through all PHP functions can take significant page execution time
    // and this function is called on every administrative page via
    // system_requirements().
    foreach (preg_grep('/_\d+$/', $functions['user']) as $function) {
      // If this function is a module update function, add it to the list of
      // module updates.
      if (preg_match($regexp, $function, $matches)) {
        $updates[$matches['module']][] = $matches['version'];
      }
    }
    

    The last line executed from drupal_get_schema_versions() is the following one.

    return empty($updates[$module]) ? FALSE : $updates[$module];
    

    If the module name is myModule.module, drupal_get_schema_versions('myModule') will return just the functions with a name that starts with myModule_update, and ends with a number; functions like mymodule_update_7120() will not be included because the regular expression used from drupal_get_schema_versions() is case sensitive. This still applies to Drupal 8, as the regular expression is still the same used in Drupal 7.

  • Some hooks are called in specific moments. For example, hook_menu(), and hook_menu_alter() are called from Drupal 7 after a module has been enabled/disabled, or when the cache for the router information is cleared; hook_init() is not invoked for cached pages.
    Once the hooks are invoked because a specific event happened, they will not called again until a similar event doesn't happen. They are not called in two successive page requests.

  • Drupal caches the list of hooks implemented from a module. If you are editing the code of an enabled module to add new hooks, you first need to disable and re-enable the module, or Drupal will not notice there are new hooks.

  • Ensure that a return statement didn't sneak its way into one of your hook functions during a refactoring. It has the potential to break not only the hook that it appears in, but to cause a chain reaction that breaks other hooks as well, making the problem difficult to locate.

  • Also maybe worth to mention my mistake for the sake of others in the future: do NOT define a namespace in your .module (or any other "flat", non-class PHP) file. Otherwise Drupal will not recognize your file, therefore won't discover the hooks defined in them. – Balu Ertl Apr 9 '19 at 13:30

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