Dynamics of Search module - Part 1 (About hooks)

Search module of Drupal is a decent effort to optimize database searching, Salient features of drupal search are CJK handling, incremental revision index update among many others. Search in drupal is not one massive component which takes care of overall site search, it rather provides a framework based on hooks (drupal way of doing things) for other modules to interact with indexing,searching process; Though its search module which does actual parsing and all nitty gritty of regular expressions.
Hooks Exposed by Search Module
There are three major hooks exposed by search module:

  • hook_search
  • any module which wanna interact with search module during site searching can implement this hook, there are various Operations which this hook takes like name,status,search etc. Any module that is implementing this hook should atleast implement 'name' op and 'search' op.
    Below is a example from user.module

     switch ($op) {
        case 'name':
          if (user_access('access user profiles')) {
            return t('Users');
          }
        case 'search':
          if (user_access('access user profiles')) {
            $find = array();
            // Replace wildcards with MySQL/PostgreSQL wildcards.
            $keys = preg_replace('!\*+!', '%', $keys);
            $result = pager_query("SELECT name, uid FROM {users} WHERE LOWER(name) LIKE LOWER('%%%s%%')", 15, 0, NULL, $keys);
            while ($account = db_fetch_object($result)) {
              $find[] = array('title' => $account->name, 'link' => url('user/'. $account->uid, NULL, NULL, TRUE));
            }
            return $find;
          }

    Here name op is used to simply let search module know what type of content is being searched for, which helps it to differentiate the results in tabs sometimes. Its the search op which actually retrieves the users based on the keyword, Here you will note that its doing a direct query on user table as user info is not part of search index because user module does not implement the second hook we are going to talk about (hook_update_index).

  • hook_update_index
  • This hook is exposed for modules to insert their module specific data into the search index, This hook finally calls search_index function to insert data into the search index .. This is a snippet from node_update_index (Implementation of hook_update_index)

    .....................
    ......................
     while ($node = db_fetch_object($result)) {
        $last_change = $node->last_change;
        $last_nid = $node->nid;
        $node = node_load($node->nid);

        // Build the node body.
        $node = node_build_content($node, FALSE, FALSE);
        $node->body = drupal_render($node->content);

        // Allow modules to modify the fully-built node.
        node_invoke_nodeapi($node, 'alter');

        $text = '<h1>'. check_plain($node->title) .'</h1>'. $node->body;

        // Fetch extra data normally not visible
        $extra = node_invoke_nodeapi($node, 'update index');
        foreach ($extra as $t) {
          $text .= $t;
        }

        // Update index
        search_index($node->nid, 'node', $text);
    ...................

    In the above code node module prepares data to be inserted into the search index, Whereas its search index which actually takes care of cleaning up the html, giving score and ranks to the content on the basis of tags and other schemes.

  • hook_search_preprocess
  • This hook is implemented by modules if they wanna do something with content before its indexed or do something with keyword before its searched in the search index, This helps drupal to handle CJK content.

There are other hooks exposed by search module which determine the look and feel of the search result or the search form like hook_search_item is a good place to alter the look and feel of the result item.

More About variables associated with search module in Part 2, Also look out for hacks and tweaks with search module (maybe Part 3?)