Drupal's Bootstrap/Dispatch/Routing Flow

4.1k views Asked by At

Assuming the minimal module install (to keep things simple), what are the core "responsibilities" of the two top level functions in Drupal's index.php?

drupal_bootstrap(DRUPAL_BOOTSTRAP_FULL);
menu_execute_active_handler();

I'm trying to understand, from a high level, how Drupal's core systems work, particularly in relationship to web based MVC. So in a Code Igniter like system, the following

  1. Examine the URL, turns it into a class and action

  2. Calls the action method on the class, where information is loaded from models, "businessy logic" is done

  3. Information is handed off to a view layer

  4. Layout system renders HTML page

  5. Part of the layout (often a "content area") is driven by the information handed off in step 3

What's the equivalent dispatch process in Drupal? I understand how the module system works, but I don't quite follow Drupal's philosophy on the how/why of data loading and theme/layout rendering, and where the handoff between the two happens.

I realize Drupal is radically different from web app MVC system; I'm trying to understand how. I realize Drupal is designe to be successfully used without fully understanding this. Preference given to Drupal 7 answers, but if there's been radical changes information from previous versions is welcome.

3

There are 3 answers

2
Henrik Opel On BEST ANSWER

Good answers from Berdir and Apemantus already (+1), but some room for an additional try:

Concerning Drupals relationship to MVC, I took a stab at the topic with this answer to a question for 'A metaphor for Drupal module's inner workings', which might fit with your request for a 'high level' overview.

As for the top level function calls - well, some things just come in threes, so I would suggest taking the theme('page, $return) call into the mix, as this will complete the overview:

drupal_bootstrap(DRUPAL_BOOTSTRAP_FULL);
$return = menu_execute_active_handler();

// Menu status constants are integers; page content is a string.
if (is_int($return)) {
  switch ($return) {
    // [...] Snipped error page handling code
  }
}
elseif (isset($return)) {
  // Print any value (including an empty string) except NULL or undefined:
  print theme('page', $return);
}
drupal_page_footer();

One by one:

  1. drupal_bootstrap()
    As the name suggests, this is mainly concerned with 'setting the stage', that is e.g.

    • Initialize basic configuration
    • Initialize database access
    • Initialize session handling
    • Identify the requesting user
    • Eventually shortcut the request by serving cached content
    • ... (more stuff)

    An important point here is that already during this phase, the hook system will invoke other modules, if they ask for it, giving them a chance to inject custom logic in this early phase. While it is not common for modules to do this, it adds to the flexibility of Drupal that it can be done for special needs like e.g. influencing the user identification process, preventing or enforcing a cache hit, rewriting the requested path and other 'low level' manipulations.

  2. menu_execute_active_handler()
    This roughly matches steps 1. and 2. from your CodeIgniter sketch. It will inspect the requested path, match it to the proper callback function (including some 'turn wildcards into parameters' logic), and invoke that callback, passing the extracted (or predefined) parameters. The callback is usually expected to return the main page content, but is free to do other stuff like e.g. just redirecting the request. Most "businessy logic" will be done here, but note that the returned content is quite often already a Markup Fragment, so this phase includes some parts of the view layer already!

  3. theme_page() (Indirectly invoked via the theme() function, which adds a lot of surrounding 'magic')
    This (very) roughly matches the usual view layer, as this is where the final assembly of the markup to be returned takes place. But it is also the place where the 'surrounding' elements of a page get assembled (think menus, headers, sidebars, etc.) so there is still a lot of potential for "businessy logic" going on during this stage as well.

During all these steps, the hook system (along with the similarly designed theme system), will provide quite a number of 'hook in' points for other modules to 'subscribe' to, if they need to. When invoked, they will get passed the relevant information being processed at that point, with the option to step in and manipulate it (or just trigger some separate processing). All this adds up to a quite flexible system (because of the huge amount of 'intercept and manipulate' options for custom modules), but is also responsible for a lot of the difficulties in learning Drupal, as the question of 'what happens when' is often not easily answered :/

So to sum it up shortly:

  1. bootstrapping - Initialization grunt work, eventually enriched with early intrusions of 'business logic'.
  2. execution - Main 'business logic' processing, already with some 'view' generation logic (assembly of Markup fragments).
  3. theming - Main Markup generation, with some significant portions of 'business logic' still in the mix.
1
Apemantus On
2
Berdir On

After the bootstrap, the only given thing that happens is the menu router system, which figures out which page callback is responsible for this request. To do that, it relies on the information that all the installed modules returned in their hook_menu() definition (this is stored in the database and only updated when explicitly requested to do so, when new modules are enabled for example).

That hook can control a lot. For example access permissions, defining arguments, title of the menu links and so on. Also, menu routers can be almost as complex as you want, they are not limited to the usual controller/action patterns. I think you can define menu router items up to 9 elements deep, for example 'yourmodule/view/%/sub/%/%/whatever'.

See http://drupal.org/node/109131 for a short overview with an example.

Inside that page callback, the providing module is free to do whatever it wants. It can use the theme system if it wants to, fire hooks or do anything else with the "content" portion of a page. The theme system will include all other portions of a themed page including other regions and other blocks that are included in those regions automatically. This is important to remember when creating callbacks that respond to AJAX request or provide things like xml feeds etc. In those cases you would need to take further steps to make adjustments in the theme to accommodate requests that shouldn't include the "rest" of the page.