DrupalKernel::initializeContainer is very complex. It has to account for several situations where module lists can change, making the code hard to understand and even harder to refactor. The usage of instance variables made methods dependent on other methods being called first, which is as hard to maintain as any of our previous bootstrap code. DrupalKernel also has a bunch of supporting methods to maintain it's module list, which doesn't make much sense considering we have a ModuleHandler class now.
This patch is an attempt to factor this code out into a ModuleHandlerFactory, which will read in the module list every time from config, much like DrupalKernel was doing. The result is a much simpler kernel with less state to maintain.
Doing this required the removal of the updateModules method as well. To try to simplify the process of the kernel being notified that the container needs to be rebuilt, I replaced all of that with a simple event and a new callback method for when the container needs to be rebuilt using the module list from config.
It's possible I missed something in the requirements, but in my limited testing, it appears to work ok.
Comment | File | Size | Author |
---|---|---|---|
#40 | 2016-04-01 16_47_32-MINGW32__c_xampp_htdocs_drupal.png | 66.58 KB | dbjpanda |
#33 | interdiff.txt | 7.16 KB | katbailey |
#33 | 2021959.module_handler_refactor.33.patch | 42.42 KB | katbailey |
#32 | interdiff.txt | 2.39 KB | katbailey |
#32 | 2021959.module_handler_refactor.32.patch | 42.88 KB | katbailey |
Comments
Comment #2
tim.plunkettkernel-module-handler-refactor.patch queued for re-testing.
Comment #3
chx CreditAttribution: chx commentedHanding off handling module data to the module handler sounds a very good idea, indeed. The devil is in the details:
ModuleHandlerFactory can be further simplied by removing moduleData() as visible http://privatepaste.com/e7148fd096 here. However, this is only possible because the module data is not reused -- and that seems bad. As far as I can see, HEAD will scan once per Kernel and updateModules will not cause a re-scan as moduleData is updated on-the-fly. Don't forget that module_enable rebuilds the container per module... and I think we added a re-scan for each. That looks bad.
I see no reason to use the event dispatcher here. Maybe if it would be injected to everyone involved but of course that's not quite possible so at the end of the day we have
I can't see the former more desirable than the latter. We do not have a per-module enable/install hook so it's not like we are replacing / amending a hook here with events.
Minor: for further simplification, initializeCachedContainer could remove $container = NULL; and return $container. Fruther, if persistServices were to return $container one could write
return $this->persistServices(new $fully_qualified_class_name, $persist);
Comment #5
tim.plunkettMissing leading \, I think that's most of the fails.
Comment #6
msonnabaum CreditAttribution: msonnabaum commentedGood catch.
Comment #8
Anonymous (not verified) CreditAttribution: Anonymous commenteda bunch of the fails are caused by the DrupalUnitTestBase::enableModules() having a new module handler without any modules in it's moduleList.
i added an extra $module_handler->setModuleList($modules), and there are still a bunch of issues, but less fatals. now i want the bot to tell us what is still borked.
Comment #10
andypostRelated: usage of container in tests is not clear #2014015: Replace drupal_container() with Drupal::service() in the simpletest module
Comment #11
katbailey CreditAttribution: katbailey commentedHere's a hilariously convoluted solution to the DUTB test problem (they were ending up with an empty module list after the 'drupal.update_modules' event was dispatched so namespaces were not being registered) - purely for experimental purposes, to see where it leaves us. I'm hoping there's an easier way to achieve the same thing...
Comment #13
andypostnew line
so \Drupal or Drupal?
also maybe better use $this->container?
Comment #14
msonnabaum CreditAttribution: msonnabaum commentedRe-roll.
Comment #16
msonnabaum CreditAttribution: msonnabaum commented#14: 2021959.module_handler_refactor.14.patch queued for re-testing.
Comment #18
katbailey CreditAttribution: katbailey commentedLet's try this...
Comment #20
katbailey CreditAttribution: katbailey commentedUgh, DUTB. It looks to me like a bunch of these tests should have been removed with this commit:
http://drupalcode.org/project/drupal.git/commitdiff/36fcf91cb57dc799790f...
module_enable() isn't properly supported for DUTB and these changes make the problem worse. Let's just insist that DUTB tests can only use
$this->enableModules()
and$this->installSchema()
.Comment #22
katbailey CreditAttribution: katbailey commentedComment #23
tim.plunkettNeeds to be one line, or just make the second sentence its own "paragraph"
Over 80 chars
Nice!
We should have @param here...
Missing the one line doc, and the actual typehint/docs for @param, and @return.
Docs needed (one line description, @param, @return)
The whole class needs docs
Needs docs
Docs. Are these worth moving to the base class?
Is this worth wrapping/reusing? If not maybe an inline comment
Comment #24
dawehnerSo.
Comment #25
andypostwhy not $this->container->get('event_dispatcher')?
any reason to drop the test?
why $module_handler is taken from \Drupal and not $this->container->get()?
Comment #26
fubhy CreditAttribution: fubhy commentedRe-roll
Comment #28
msonnabaum CreditAttribution: msonnabaum commentedReroll.
Comment #29
msonnabaum CreditAttribution: msonnabaum commentedThis should take care of tim's concerns in #23, with the exception of 9 and 10. I didn't write that code, so I'll let Kat field those.
@andypost Concerning $this->container vs Drupal::service, there are already calls to Drupal::service in that class, so fixing it is beyond the scope of this issue. Also, pretty sure the test removal is covered in #20.
This patch also cleans up some leftover methods that weren't actually used and renames a couple methods on the factory to be more clear.
Comment #32
katbailey CreditAttribution: katbailey commentedThis should fix those tests. Basically we can't use the moduleHandler directly in DUTB tests because they are special. Whether this makes a mockery of those tests I don't know as I'm not familiar with the purpose of the tests in question. What I do know is that the monstrosity that is DUTB should not stand in the way of such an important refactoring of something so fundamental to Drupal core.
I still haven't addressed Tim's points 9 and 10 above but will do because that code is brittle as hell. Not sure it makes sense to put methods in the UnitTestBase class because the only non-DUTB test that needs this behavior is DrupalKernelTest, which is special. Special-- :(
Comment #33
katbailey CreditAttribution: katbailey commentedThis addresses points 9 and 10 in #23 - I added the bootrap config related stuff to UnitTestBase.
Comment #34
donquixote CreditAttribution: donquixote commentedI am going to attempt to reroll / un-conflict this, now that #2016629: Refactor bootstrap to better utilize the kernel is in.
Not sure how far I get before I give up! It looks scary.
If someone else wants to take over or help ou, let me know on IRC.
Comment #35
donquixote CreditAttribution: donquixote commentedNope, I give up.
Rerolling would be more difficult than doing it from scratch, I'm afraid.
Going for a new attempt on top of #2279423: Low-level DIC for low-level services: Testing grounds. (I originally wanted to do it the other way round)
Comment #36
neclimdulComment #37
mgiffordComment #38
znerol CreditAttribution: znerol commentedComment #39
mgiffordThere has been no new work on this issue in quite some time. So I'm assuming the person assigned is no longer being actively pursuing it. Sincere apologies if this is wrong.
Comment #40
dbjpanda CreditAttribution: dbjpanda commentedGetting a lots of conflicts while rerolling. Need an experienced developer to reroll.
Comment #41
vprocessor CreditAttribution: vprocessor at Skilld commentedComment #42
vprocessor CreditAttribution: vprocessor at Skilld commentedComment #44
hitesh-jain CreditAttribution: hitesh-jain at Acquia commentedComment #45
hitesh-jain CreditAttribution: hitesh-jain at Acquia commentedComment #47
hitesh-jain CreditAttribution: hitesh-jain at Acquia commentedComment #48
hitesh-jain CreditAttribution: hitesh-jain at Acquia commentedComment #49
xiwar CreditAttribution: xiwar at Redweb commentedHi, i'm Matt Lambert from Redweb. I am going to reroll.
Comment #50
xiwar CreditAttribution: xiwar at Redweb commentedComment #52
GoZ CreditAttribution: GoZ at Barbe-Rousse commentedA lot of things has moved since the last patch has been done for 8.0.x.
This needs lot of work to apply on 8.4.x
Comment #55
almaudoh CreditAttribution: almaudoh commentedIs this still relevant? Considering how much the DrupalKernel and ModuleHandler have changed?
Comment #57
markhalliwellYes, a lot has changed, but I think maybe we can instead close this as a dup of #2941757: Extension System, Part IV: Properly register all installed extensions/namespaces during container generation.
I agree that the basic premise is the same though: "what we currently has is hardcoded and sucks; needs to be refactored to better handle [all] installed extensions"
I'll look at the patches here to see what I can salvage.