DoctrineMigrationsExtension   A
last analyzed

Complexity

Total Complexity 22

Size/Duplication

Total Lines 127
Duplicated Lines 0 %

Test Coverage

Coverage 89.06%

Importance

Changes 1
Bugs 0 Features 1
Metric Value
wmc 22
eloc 58
c 1
b 0
f 1
dl 0
loc 127
ccs 57
cts 64
cp 0.8906
rs 10

5 Methods

Rating   Name   Duplication   Size   Complexity  
A getNamespace() 0 3 1
A getXsdValidationBasePath() 0 3 1
F load() 0 77 15
A getBundlePath() 0 13 2
A checkIfBundleRelativePath() 0 11 3
1
<?php
2
3
declare(strict_types=1);
4
5
namespace Doctrine\Bundle\MigrationsBundle\DependencyInjection;
6
7
use Doctrine\Migrations\Metadata\Storage\MetadataStorage;
8
use Doctrine\Migrations\Metadata\Storage\TableMetadataStorageConfiguration;
9
use InvalidArgumentException;
10
use RuntimeException;
11
use Symfony\Component\Config\FileLocator;
12
use Symfony\Component\DependencyInjection\Argument\ServiceClosureArgument;
13
use Symfony\Component\DependencyInjection\ContainerBuilder;
14
use Symfony\Component\DependencyInjection\Definition;
15
use Symfony\Component\DependencyInjection\Loader\XmlFileLoader;
16
use Symfony\Component\DependencyInjection\Reference;
17
use Symfony\Component\HttpKernel\DependencyInjection\Extension;
18
use function array_keys;
19
use function explode;
20
use function implode;
21
use function sprintf;
22
use function strlen;
23
use function substr;
24
25
/**
26
 * DoctrineMigrationsExtension.
27
 */
28
class DoctrineMigrationsExtension extends Extension
29
{
30
    /**
31
     * Responds to the migrations configuration parameter.
32
     *
33
     * @param string[][] $configs
34
     */
35 26
    public function load(array $configs, ContainerBuilder $container) : void
36
    {
37 26
        $configuration = new Configuration();
38
39 26
        $config = $this->processConfiguration($configuration, $configs);
40
41 25
        $locator = new FileLocator(__DIR__ . '/../Resources/config/');
42 25
        $loader  = new XmlFileLoader($container, $locator);
43
44 25
        $loader->load('services.xml');
45
46 25
        $configurationDefinition = $container->getDefinition('doctrine.migrations.configuration');
47
48 25
        foreach ($config['migrations_paths'] as $ns => $path) {
49 22
            $path = $this->checkIfBundleRelativePath($path, $container);
50 22
            $configurationDefinition->addMethodCall('addMigrationsDirectory', [$ns, $path]);
51
        }
52
53 25
        foreach ($config['migrations'] as $migrationClass) {
54 2
            $configurationDefinition->addMethodCall('addMigrationClass', [$migrationClass]);
55
        }
56
57 25
        if ($config['organize_migrations'] !== false) {
58 2
            $configurationDefinition->addMethodCall('setMigrationOrganization', [$config['organize_migrations']]);
59
        }
60
61 25
        if ($config['custom_template'] !== null) {
62
            $configurationDefinition->addMethodCall('setCustomTemplate', [$config['custom_template']]);
63
        }
64
65 25
        $configurationDefinition->addMethodCall('setAllOrNothing', [$config['all_or_nothing']]);
66 25
        $configurationDefinition->addMethodCall('setCheckDatabasePlatform', [$config['check_database_platform']]);
67
68 25
        $diDefinition = $container->getDefinition('doctrine.migrations.dependency_factory');
69
70 25
        foreach ($config['services'] as $doctrineId => $symfonyId) {
71 3
            $diDefinition->addMethodCall('setDefinition', [$doctrineId, new ServiceClosureArgument(new Reference($symfonyId))]);
72
        }
73
74 25
        foreach ($config['factories'] as $doctrineId => $symfonyId) {
75 1
            $diDefinition->addMethodCall('setDefinition', [$doctrineId, new Reference($symfonyId)]);
76
        }
77
78 25
        if (! isset($config['services'][MetadataStorage::class])) {
79 24
            $storageConfiguration = $config['storage']['table_storage'];
80
81 24
            $storageDefinition = new Definition(TableMetadataStorageConfiguration::class);
82 24
            $container->setDefinition('doctrine.migrations.storage.table_storage', $storageDefinition);
83 24
            $container->setAlias('doctrine.migrations.metadata_storage', 'doctrine.migrations.storage.table_storage');
84
85 24
            if ($storageConfiguration['table_name']!== null) {
86 2
                $storageDefinition->addMethodCall('setTableName', [$storageConfiguration['table_name']]);
87
            }
88 24
            if ($storageConfiguration['version_column_name']!== null) {
89 2
                $storageDefinition->addMethodCall('setVersionColumnName', [$storageConfiguration['version_column_name']]);
90
            }
91 24
            if ($storageConfiguration['version_column_length']!== null) {
92 2
                $storageDefinition->addMethodCall('setVersionColumnLength', [$storageConfiguration['version_column_length']]);
93
            }
94 24
            if ($storageConfiguration['executed_at_column_name']!== null) {
95 2
                $storageDefinition->addMethodCall('setExecutedAtColumnName', [$storageConfiguration['executed_at_column_name']]);
96
            }
97 24
            if ($storageConfiguration['execution_time_column_name']!== null) {
98 2
                $storageDefinition->addMethodCall('setExecutionTimeColumnName', [$storageConfiguration['execution_time_column_name']]);
99
            }
100
101 24
            $configurationDefinition->addMethodCall('setMetadataStorageConfiguration', [new Reference('doctrine.migrations.storage.table_storage')]);
102
        }
103
104 25
        if ($config['em'] !== null && $config['connection'] !== null) {
105 1
            throw new InvalidArgumentException(
106 1
                'You cannot specify both "connection" and "em" in the DoctrineMigrationsBundle configurations.'
107
            );
108
        }
109
110 24
        $container->setParameter('doctrine.migrations.preferred_em', $config['em']);
111 24
        $container->setParameter('doctrine.migrations.preferred_connection', $config['connection']);
112 24
    }
113
114 22
    private function checkIfBundleRelativePath(string $path, ContainerBuilder $container) : string
115
    {
116 22
        if (isset($path[0]) && $path[0] === '@') {
117 1
            $pathParts  = explode('/', $path);
118 1
            $bundleName = substr($pathParts[0], 1);
119
120 1
            $bundlePath = $this->getBundlePath($bundleName, $container);
121 1
            return $bundlePath . substr($path, strlen('@' . $bundleName));
122
        }
123
124 21
        return $path;
125
    }
126
127 1
    private function getBundlePath(string $bundleName, ContainerBuilder $container) : string
128
    {
129 1
        $bundleMetadata = $container->getParameter('kernel.bundles_metadata');
130
131 1
        if (! isset($bundleMetadata[$bundleName])) {
132
            throw new RuntimeException(sprintf(
133
                'The bundle "%s" has not been registered, available bundles: %s',
134
                $bundleName,
135
                implode(', ', array_keys($bundleMetadata))
136
            ));
137
        }
138
139 1
        return $bundleMetadata[$bundleName]['path'];
140
    }
141
142
    /**
143
     * Returns the base path for the XSD files.
144
     *
145
     * @return string The XSD base path
146
     */
147
    public function getXsdValidationBasePath() : string
148
    {
149
        return __DIR__ . '/../Resources/config/schema';
150
    }
151
152 1
    public function getNamespace() : string
153
    {
154 1
        return 'http://symfony.com/schema/dic/doctrine/migrations/3.0';
155
    }
156
}
157