Hi everyone.
Firstly, sorry for my bad English.
I am currently investigating “Laminas” components working in conjunction with “Mezzio”. My general work related to Magento framework and there is a great feature which related to dependencies management. I mean virtual types. In short Virtual types are ability to create multiple instances of the same class with different constructor parameters.
I’ve found in laminas something simillar. In “Laminas-Di” documentation I found this example:
use Laminas\Di\Injector;
use Laminas\Di\Config;
$injector = new Injector(new Config([
'preferences' => [
FooInterface::class => Foo::class,
],
'types' => [
'MyClass.A' => [
'typeOf' => MyClass::class,
'preferences' => [
FooInterface::class => SpecialFoo::class,
],
],
'MyClass.B' => [
'typeOf' => MyClass::class,
'preferences' => [
FooInterface::class => Bar::class,
],
],
],
]));
In my case I need make two instances of \Mezzio\LaminasView\LaminasViewRenderer. LaminasViewRenderer has the next constructor specification:
public function __construct(RendererInterface $renderer = null, $layout = null, string $defaultSuffix = null)
I need that the $renderer param will be resolved using psr container, $layout must be ‘admin::layout’ and $suffix may be null for viewRenderer of admin part and the same things for viewRenderer of public part, but $layout must be ‘default::layout’.
inside Admin\ConfigProvider I’ve placed next code:
class ConfigProvider
{
public function __invoke(): array
{
return [
'dependencies' => $this->getDependencies(),
];
}
public function getDependencies(): array
{
return [
'auto' => [
'types' => [
TemplateRenderer\AdminTemplateRendererInterface::class => [
'typeOf' => \Mezzio\LaminasView\LaminasViewRenderer::class,
'parameters' => [
'renderer' => '*',
'layout' => 'admin::layout',
'defaultSuffix' => '*',
]
]
]
]
];
}
I expected that I get LaminasViewRenderer instance with ‘admin::layout’ predefined parameter inside auto generated factory. But after I run di-generate-aot (as discribed here https://docs.laminas.dev/laminas-di/cookbook/aot-guide/) script I’ve got next factories class code:
final class AdminTemplateRendererInterfaceFactory implements FactoryInterface
{
public function create(ContainerInterface $container, array $options = [])
{
$args = empty($options)
? [
null, // renderer
null, // layout !!! I expected that 'admin::layout' string be here
null, // defaultSuffix
]
: [
array_key_exists('renderer', $options) ? $options['renderer'] : null,
array_key_exists('layout', $options) ? $options['layout'] : null,
array_key_exists('defaultSuffix', $options) ? $options['defaultSuffix'] : null,
];
return new \Mezzio\LaminasView\LaminasViewRenderer(...$args);
}
I spent some time for debugging and found out that when DependencyResolver try to configure injection then it search configured params using class name which pointed at the typeOf.
I am not sure but it seems to me a “layout” parameter should be searched by alias to get right result. Currently it returns nothing because there is no key with a LaminasViewRenderer type. And it not make sense. I need create different instances of LaminasViewRenderer that why I used aliases. And then I will get this instances by their aliases.
hope I explained well.
Please explain. Am I doing somethink wrong or maybe it is a wrong behaviour of the dependency params resolver?
Great thanks.