I'm trying to automatically load entity mappings based on a folder structure. My loader class returns a map like this array below. My goal is to find all "capabilities" and map their domain folder to the doctrine ORM entity mapping when the app is initialized.
[
"UploadsDomain" => [
"alias" => "SomeNameDomain",
"dir" => "/home/someName/projects/video-service/src/Capability/SomeName/Domain",
"is_bundle" => false,
"prefix" => "App\Capability\SomeName\Domain",
"type" => "attribute",
]
]
My compiler pass is this, and I'm calling it in my Kernel.php $container->addCompilerPass(new DoctrineMappingPass());
.
namespace App\DependencyInjection\Compiler;
use App\Doctrine\CapabilityMappingLoader;
use Doctrine\ORM\Mapping\Driver\AttributeDriver;
use Symfony\Component\DependencyInjection\Compiler\CompilerPassInterface;
use Symfony\Component\DependencyInjection\ContainerBuilder;
class DoctrineMappingPass implements CompilerPassInterface
{
public function process(ContainerBuilder $container): void
{
if (!$container->hasDefinition('doctrine.orm.default_configuration')) {
return;
}
$definition = $container->getDefinition('doctrine.orm.default_configuration');
// Instantiate the mapping loader
$loader = new CapabilityMappingLoader();
$mappings = $loader->loadMappings();
foreach ($mappings as $alias => $mapping) {
$definition->addMethodCall('addEntityNamespace', [$alias, $mapping['prefix']]);
$definition->addMethodCall('setMetadataDriverImpl', [
new AttributeDriver([$mapping['dir']]),
]);
}
}
}
However, for some reason I get this error message:
Symfony\Component\DependencyInjection\Exception\RuntimeException: Unable to dump a service container if a parameter is an object or a resource, got "Doctrine\ORM\Mapping\Driver\AttributeDriver".
Any idea how I can get this to work?
You are passing a concrete instance of AttributeDriver
to addMethodCall
.
Try creating a service definition for each needed AttributeDriver
instance.
I think this should get you going, or at least moving in the right direction:
(This incorporates a couple of fixes from floriank after they tested the code).
class DoctrineMappingPass implements CompilerPassInterface
{
public function process(ContainerBuilder $container): void
{
if (!$container->hasDefinition('doctrine.orm.default_configuration')) {
return;
}
$definition = $container->getDefinition('doctrine.orm.default_configuration');
// Instantiate the mapping loader
$loader = new CapabilityMappingLoader();
$mappings = $loader->loadMappings();
foreach ($mappings as $mapping) {
$paths = [$mapping['dir']];
$attributeDefinition = new Definition(AttributeDriver::class, [$paths]);
$array = [$mapping['prefix']];
$definition->addMethodCall('setEntityNamespaces', [$array]);
$definition->addMethodCall('setMetadataDriverImpl', [$attributeDefinition]);
}
}
}