User tests: Successful: Unsuccessful:
This PR adds the ability to override container configuration by creating a special bootstrap.php file in the root directory. This allows developers to:
It works similarly to defines.php.
This is a very simple event listener created without a plugin:
<?php
\defined('_JEXEC') or die;
use Joomla\Event\DispatcherInterface;
use Joomla\Event\EventInterface;
$container->get(DispatcherInterface::class)->addListener('onAfterRoute', function (EventInterface $event) {
echo $event->getName();
});This is a more advanced example showing how to implement DKIM for mailer:
<?php
\defined('_JEXEC') or die;
use Joomla\CMS\Mail\MailerFactoryInterface;
use Joomla\CMS\Mail\MailerInterface;
use Joomla\DI\Container;
use Joomla\Registry\Registry;
/** @var \Joomla\DI\Container $container */
function unprotect(Container $container, string $key): Container
{
$resource = $container->getResource($key);
$reflection = (new \ReflectionClass($resource));
$property = $reflection->getProperty('protected');
$property->setValue($resource, false);
return $container;
}
unprotect($container, MailerFactoryInterface::class);
$container->extend(MailerFactoryInterface::class, function (MailerFactoryInterface $factory) {
return new class ($factory) implements MailerFactoryInterface {
public function __construct(
private MailerFactoryInterface $factory
) {
}
public function createMailer(?Registry $settings = null): MailerInterface
{
$mailer = $this->factory->createMailer($settings);
$mailer->DKIM_domain = substr(strrchr($mailer->From, '@'), 1);
$mailer->DKIM_identity = $mailer->From;
$mailer->DKIM_private = '/path/to/private/key';
$mailer->DKIM_selector = 'phpmailer';
return $mailer;
}
};
});Create a bootstrap.php file in the root directory with the following content:
<?php
\defined('_JEXEC') or die;
use Joomla\Event\DispatcherInterface;
use Joomla\Event\EventInterface;
$container->get(DispatcherInterface::class)->addListener('onAfterRoute', function (EventInterface $event) {
echo $event->getName();
});Reload the page and ensure that the value onAfterRoute is present on the page.
You shouldn't see the onAfterRoute value on the page.
The onAfterRoute value should be displayed.
Please select:
Documentation link for guide.joomla.org:
No documentation changes for guide.joomla.org needed
Pull Request link for manual.joomla.org:
No documentation changes for manual.joomla.org needed
| Status | New | ⇒ | Pending |
| Category | ⇒ | Administration CLI |
| Labels |
Added:
PR-6.1-dev
|
||
@HLeithner, plugins are triggered too late to use them for extending some services like Application::class , Database::class and so on.
The point it that the application is the core of joomla till now it's not intended to change this, database can be replaced, I do this with my own extension.
you have one alternative before all of this, use the define.php in the root folder might could do this kind of hack.
@HLeithner, if I understand properly how plugins work, Joomla loads a list of activated plugins from the database using DatabaseInterface::class service, right? If you override database service using plugin one part of Joomla will use the old database service instance and the other part will use the new overrided one.
When you want to change the database for all, then it is better to change it in the configuration.php.
@HLeithner, if I understand properly how plugins work, Joomla loads a list of activated plugins from the database using
DatabaseInterface::classservice, right? If you override database service using plugin one part of Joomla will use the old database service instance and the other part will use the new overrided one.
yes that's the way, or you add your own database driver to the configuration.php which I actually do at the moment, but both is possible.
What do you want to change globally in the database driver?
@laoneo, I don't need to extend database service right now. I just answered to @HLeithner's question why this feature would be useful, because in some cases we can't use plugins for services overriding.
For this we have plugins with priority settings, so I'm not sure why this should be needed.