Extensions use hooks to insert functionality at different places of mediawiki, but there is no proper way to share non-core data between hook handlers. Yet this is often needed, for example the Cite extension needs to use the same Cite object between its different parser hooks, FlaggedRevs needs the same FlaggableWikiPage and FlaggablePageView objects between its various hooks, etc.
Workarounds against this limitation consist mostly in adding a custom field to the shared core object or making a static instance of the needed extension object. The former is a hack, even if allowed by PHP it should be avoided, and this can require cloning the objects or checking if they are the same. The latter is unsatisfactory, there may be several instances of the underlying core object or it may change in unanticipated ways (when anticipated, this requires clearing and recreating the instance).
As suchn additional issue is that all hook handlers are forced to be bundled together in a huge class of static methods. This has significant drawbacks: the code is hard to follow, the dependencies are obscure and it can't be unit tested. The underlying problem is the same: hook handlers are static, we nenot linked to provide extensions with a unified and reliable way to pass informathe objects they're meant to extend the function between hooksality of.
One possibility is to refine the custom field workaround, by holding an array of extension-defined objects associated to a core object. Each may be called a "hooked instance". For example, to each WikiPage instance, FlaggedRevs could associate a FlaggableWikiPage. One would need to add a getHookedInstance( $class ) method to core classes supporting this, maybe using a trait.As such, The method would return the instance of the requested classwe need to provide extensions with a unified and reliable way to pass information between hooks, creating it on first call by calling a factory method of the requested class that wand the flow of it should only depend on the core classbe clearer.
This also mitigates another issue: that all hook handlers are forced to be bundled together in a huge class of static methods. This has significant drawbacks: the code is hard to follow, the dependencies are obscure and it can't be unit tested.One possibility is to "hook" an extension object to a core object, We could refactor complex hook handlers as methods in a hooked classfor example Cite to Parser and FlaggableWikiPage to WikPage.
To realize the full potential of this idea, it may be useful to add some transversal objects for extensions to hook into, e.g. a Change object that is available from the start of an action request to the recent change save (providing context and additional data about the requested change and its processing)hen a hook run from the core object has its handler as a method of the hooked extension object.