ZF-7089: Zend_Application_Resource_Modules::init() bootstraps all existing module bootstrap classes regardless of request

Issue Type: Bug Created: 2009-06-22T16:34:35.000+0000 Last Updated: 2009-09-30T05:22:58.000+0000 Status: Resolved Fix version(s): Reporter: Matthijs van den Bos ( Assignee: Matthew Weier O'Phinney (matthew) Tags: - Zend_Application

Related issues: - ZF-7095



h4. Behaviour: In Zend_Application_Resource_Modules::init(), all Bootstrap classes for all modules are loaded, regardless of what module was requested.

h4. Effect: This has the following side-effect: config ini keys that are set for each module are overwritten by each module when its bootstrap() method is called. The (unwanted) result is that the key is set for the last module encountered, not for the module requested.

h4. Example: setting layout resource in the config ini:

<pre class="literal">resources.layout.layout = "default"

resources.modules[] =
extranet.resources.layout.layout = "extranet"
intranet.resources.layout.layout = "intranet"

Also the module paths are not set explicitly, but by only setting

<pre class="literal"> 
That means modules are registered in the order they are encountered when iterating through the modules directory.

h4. Result: 
the layout is set to 'intranet', even if the default or extranet module were requested.

h4. Suggested solution:
Zend_Application_Resource_Modules::init() should check for the requested module and only instantiate that bootstrap class.

The problem is that the request is not yet set in the frontcontroller when this is run. Is there a workaround?
If the request was set, it could be something like this:

the foreach starting on line 65:

foreach (array_keys($modules) as $module) { if ($module === $default) { continue; }



<pre class="literal"> 

should be changed to:

$current = $front->getRequest()->getModuleName(); foreach (array_keys($modules) as $module) { if ($module === $default) { continue; } if ($module === $current) { continue; }




Posted by Thierry Jossermoz ( on 2009-06-22T20:38:10.000+0000

That's indeed a bit unclear how the modules resource is tied to the actual application modules.

A solution could be to delegate the role of bootstrapping the modules to a plugin on routeShutdown.

This can be done by replacing the following line in Zend_Application_Resource_Modules

<pre class="literal"> 

by this one

and creating a Zend_Controller_Plugin_ModulesBootstrapper plugin as follows:

<pre class="literal"> class Zend_Controller_Plugin_ModulesBootstrapper extends Zend_Controller_Plugin_Abstract
    public function routeShutdown(Zend_Controller_Request_Abstract $request)

        $bootstrap = Zend_Controller_Front::getInstance()->getParam('bootstrap');

        $bootstraps = $bootstrap->getResource('modules');
        $module = $request->getModuleName();
        if (isset($bootstraps[$module])) {


Although the side effects of this method need to be evaluated.

Posted by Thierry Jossermoz ( on 2009-06-22T20:57:33.000+0000

Quick precision: ````

is actually to be added after the foreach.

Posted by Matthew Weier O'Phinney (matthew) on 2009-06-23T04:35:21.000+0000

There were some specific problems addressed in the design goals of Zend_Application: * Autoloading for all modules should be setup up-front. This way code may selectively use information from any module without needing to know where that module resides. * Modules may need to setup front controller plugins; in particular, any given module may need to setup routes appropriate to its own controllers. The appropriate time to do this is during bootstrapping, as new routeStartup() plugins may not be added during routeStartup(). * Bootstrapping occurs prior to dispatch, and thus is request agnostic. This is to facilitate the re-use of bootstrapping in order to create service end points, one-off scripts, and to bootstrap tests. Thus, bootstrapping must occur outside of the front controller dispatch loop.

What you are suggesting goes counter to these goals entirely, and is actually impossible in the current design. The module is not known until after routing -- and routing happens during the front controller dispatch sequence. Additionally, based on the sequence of actions triggered, the module selected may change (as an example, if an exception is thrown, the ErrorController in the default module will likely be selected). I'd recommend registering a postDispatch() plugin either from your individual modules or at the application level that selects the layout based on the module.

Posted by Diego Malatesta (diego.malatesta) on 2009-09-30T05:22:56.000+0000

As I've also made the same mistake as Matthijs, I think that the whole point of Zend_Application_Resource_Modules should be better clarified in the docs, as it's a bit confusing right now (in my opinion). Thanks.

Have you found an issue?

See the Overview section for more details.


© 2006-2018 by Zend, a Rogue Wave Company. Made with by awesome contributors.

This website is built using zend-expressive and it runs on PHP 7.