GitHub Access Token became invalid

It seems like the GitHub access token used for retrieving details about this repository from GitHub became invalid. This might prevent certain types of inspections from being run (in particular, everything related to pull requests).
Please ask an admin of your repository to re-new the access token on this website.
Completed
Pull Request — master (#138)
by joseph
96:08 queued 65:06
created

Container::getConfig()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 3
Code Lines 1

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 2
CRAP Score 1

Importance

Changes 0
Metric Value
eloc 1
dl 0
loc 3
ccs 2
cts 2
cp 1
rs 10
c 0
b 0
f 0
cc 1
nc 1
nop 1
crap 1
1
<?php declare(strict_types=1);
2
3
namespace EdmondsCommerce\DoctrineStaticMeta;
4
5
use Doctrine\Common\Cache\ArrayCache;
6
use Doctrine\Common\Cache\Cache;
7
use Doctrine\Common\Cache\FilesystemCache;
8
use Doctrine\ORM\EntityManagerInterface;
9
use Doctrine\ORM\Tools\SchemaTool;
10
use Doctrine\ORM\Tools\SchemaValidator;
11
use EdmondsCommerce\DoctrineStaticMeta\Builder\Builder;
12
use EdmondsCommerce\DoctrineStaticMeta\CodeGeneration\CodeHelper;
13
use EdmondsCommerce\DoctrineStaticMeta\CodeGeneration\Command\GenerateEmbeddableFromArchetypeCommand;
14
use EdmondsCommerce\DoctrineStaticMeta\CodeGeneration\Command\GenerateEntityCommand;
15
use EdmondsCommerce\DoctrineStaticMeta\CodeGeneration\Command\GenerateFieldCommand;
16
use EdmondsCommerce\DoctrineStaticMeta\CodeGeneration\Command\GenerateRelationsCommand;
17
use EdmondsCommerce\DoctrineStaticMeta\CodeGeneration\Command\OverrideCreateCommand;
18
use EdmondsCommerce\DoctrineStaticMeta\CodeGeneration\Command\OverridesUpdateCommand;
19
use EdmondsCommerce\DoctrineStaticMeta\CodeGeneration\Command\RemoveUnusedRelationsCommand;
20
use EdmondsCommerce\DoctrineStaticMeta\CodeGeneration\Command\SetEmbeddableCommand;
21
use EdmondsCommerce\DoctrineStaticMeta\CodeGeneration\Command\SetFieldCommand;
22
use EdmondsCommerce\DoctrineStaticMeta\CodeGeneration\Command\SetRelationCommand;
23
use EdmondsCommerce\DoctrineStaticMeta\CodeGeneration\Generator\Embeddable\ArchetypeEmbeddableGenerator;
24
use EdmondsCommerce\DoctrineStaticMeta\CodeGeneration\Generator\Embeddable\EntityEmbeddableSetter;
25
use EdmondsCommerce\DoctrineStaticMeta\CodeGeneration\Generator\EntityGenerator;
26
use EdmondsCommerce\DoctrineStaticMeta\CodeGeneration\Generator\Field\AbstractTestFakerDataProviderUpdater;
27
use EdmondsCommerce\DoctrineStaticMeta\CodeGeneration\Generator\Field\EntityFieldSetter;
28
use EdmondsCommerce\DoctrineStaticMeta\CodeGeneration\Generator\Field\FieldGenerator;
29
use EdmondsCommerce\DoctrineStaticMeta\CodeGeneration\Generator\Field\StandardLibraryTestGenerator;
30
use EdmondsCommerce\DoctrineStaticMeta\CodeGeneration\Generator\FileCreationTransaction;
31
use EdmondsCommerce\DoctrineStaticMeta\CodeGeneration\Generator\FindAndReplaceHelper;
32
use EdmondsCommerce\DoctrineStaticMeta\CodeGeneration\Generator\RelationsGenerator;
33
use EdmondsCommerce\DoctrineStaticMeta\CodeGeneration\NamespaceHelper;
34
use EdmondsCommerce\DoctrineStaticMeta\CodeGeneration\PathHelper;
35
use EdmondsCommerce\DoctrineStaticMeta\CodeGeneration\PostProcessor\FileOverrider;
36
use EdmondsCommerce\DoctrineStaticMeta\CodeGeneration\TypeHelper;
37
use EdmondsCommerce\DoctrineStaticMeta\CodeGeneration\UnusedRelationsRemover;
38
use EdmondsCommerce\DoctrineStaticMeta\Di\CompilerPass\EntityDependencyPass;
0 ignored issues
show
Bug introduced by
The type EdmondsCommerce\Doctrine...ss\EntityDependencyPass was not found. Maybe you did not declare it correctly or list all dependencies?

The issue could also be caused by a filter entry in the build configuration. If the path has been excluded in your configuration, e.g. excluded_paths: ["lib/*"], you can move it to the dependency path list as follows:

filter:
    dependency_paths: ["lib/*"]

For further information see https://scrutinizer-ci.com/docs/tools/php/php-scrutinizer/#list-dependency-paths

Loading history...
39
use EdmondsCommerce\DoctrineStaticMeta\Entity\Factory\EntityDependencyInjector;
40
use EdmondsCommerce\DoctrineStaticMeta\Entity\Factory\EntityFactory;
41
use EdmondsCommerce\DoctrineStaticMeta\Entity\Interfaces\Validation\EntityValidatorInterface;
42
use EdmondsCommerce\DoctrineStaticMeta\Entity\Repositories\RepositoryFactory;
43
use EdmondsCommerce\DoctrineStaticMeta\Entity\Savers\BulkEntitySaver;
44
use EdmondsCommerce\DoctrineStaticMeta\Entity\Savers\EntitySaver;
45
use EdmondsCommerce\DoctrineStaticMeta\Entity\Savers\EntitySaverFactory;
46
use EdmondsCommerce\DoctrineStaticMeta\Entity\Testing\EntityGenerator\TestEntityGeneratorFactory;
47
use EdmondsCommerce\DoctrineStaticMeta\Entity\Validation\EntityValidator;
48
use EdmondsCommerce\DoctrineStaticMeta\Entity\Validation\EntityValidatorFactory;
49
use EdmondsCommerce\DoctrineStaticMeta\EntityManager\EntityManagerFactory;
50
use EdmondsCommerce\DoctrineStaticMeta\Exception\DoctrineStaticMetaException;
51
use EdmondsCommerce\DoctrineStaticMeta\Schema\Database;
52
use EdmondsCommerce\DoctrineStaticMeta\Schema\Schema;
53
use EdmondsCommerce\DoctrineStaticMeta\Tests\Assets\TestCodeGenerator;
54
use Psr\Container\ContainerExceptionInterface;
55
use Psr\Container\ContainerInterface;
56
use Psr\Container\NotFoundExceptionInterface;
57
use Symfony\Component\DependencyInjection\ContainerBuilder;
58
use Symfony\Component\DependencyInjection\Dumper\PhpDumper;
59
use Symfony\Component\DependencyInjection\Exception\InvalidArgumentException;
60
use Symfony\Component\DependencyInjection\Exception\ServiceNotFoundException;
61
use Symfony\Component\DependencyInjection\Reference;
62
use Symfony\Component\Filesystem\Filesystem;
63
use Symfony\Component\Validator\Mapping\Cache\DoctrineCache;
64
65
/**
66
 * Class Container
67
 *
68
 * @package EdmondsCommerce\DoctrineStaticMeta
69
 * @SuppressWarnings(PHPMD.CouplingBetweenObjects)
70
 */
71
class Container implements ContainerInterface
72
{
73
    /**
74
     * This is the list of services managed by this container
75
     *
76
     * This list is used to also generate a PHPStorm meta data file which assists with dynamic type hinting when using
77
     * the container as a service locator
78
     *
79
     * @see ./../../.phpstorm.meta.php/container.meta.php
80
     */
81
    public const SERVICES = [
82
        AbstractTestFakerDataProviderUpdater::class,
83
        ArchetypeEmbeddableGenerator::class,
84
        ArrayCache::class,
85
        Builder::class,
86
        BulkEntitySaver::class,
87
        CodeHelper::class,
88
        Config::class,
89
        Database::class,
90
        DoctrineCache::class,
91
        EntityDependencyInjector::class,
92
        EntityEmbeddableSetter::class,
93
        EntityFactory::class,
94
        EntityFieldSetter::class,
95
        EntityGenerator::class,
96
        EntityManagerFactory::class,
97
        EntityManagerInterface::class,
98
        EntitySaver::class,
99
        EntitySaverFactory::class,
100
        EntityValidator::class,
101
        EntityValidatorFactory::class,
102
        FieldGenerator::class,
103
        FileCreationTransaction::class,
104
        FileOverrider::class,
105
        Filesystem::class,
106
        FilesystemCache::class,
107
        FindAndReplaceHelper::class,
108
        GenerateEmbeddableFromArchetypeCommand::class,
109
        GenerateEntityCommand::class,
110
        GenerateFieldCommand::class,
111
        GenerateRelationsCommand::class,
112
        NamespaceHelper::class,
113
        OverrideCreateCommand::class,
114
        OverridesUpdateCommand::class,
115
        PathHelper::class,
116
        RelationsGenerator::class,
117
        RelationsGenerator::class,
118
        RemoveUnusedRelationsCommand::class,
119
        RepositoryFactory::class,
120
        Schema::class,
121
        Schema::class,
122
        SchemaTool::class,
123
        SchemaValidator::class,
124
        SetEmbeddableCommand::class,
125
        SetFieldCommand::class,
126
        SetRelationCommand::class,
127
        StandardLibraryTestGenerator::class,
128
        TestCodeGenerator::class,
129
        TestEntityGeneratorFactory::class,
130
        TypeHelper::class,
131
        UnusedRelationsRemover::class,
132
    ];
133
134
135
    /**
136
     * The directory that container cache files will be stored
137
     */
138
    public const CACHE_PATH = __DIR__ . '/../cache/';
139
140
    public const SYMFONY_CACHE_PATH = self::CACHE_PATH . '/container.symfony.php';
141
142
    /**
143
     * @var bool
144
     */
145
    private $useCache = false;
146
147
    /**
148
     * @var ContainerInterface
149
     */
150
    private $container;
151
152
    /**
153
     * @param bool $useCache
154
     *
155
     * @return Container
156
     */
157
    public function setUseCache(bool $useCache): Container
158
    {
159
        $this->useCache = $useCache;
160
161
        return $this;
162
    }
163
164
    /**
165
     * @param array $server - normally you would pass in $_SERVER
166
     *
167
     * @throws DoctrineStaticMetaException
168
     */
169 1
    public function buildSymfonyContainer(array $server): void
170
    {
171 1
        if (true === $this->useCache && file_exists(self::SYMFONY_CACHE_PATH)) {
172
            /** @noinspection PhpIncludeInspection */
173
            require self::SYMFONY_CACHE_PATH;
174
            $this->setContainer(new \ProjectServiceContainer());
175
176
            return;
177
        }
178
179
        try {
180 1
            $container = new ContainerBuilder();
181 1
            $this->addConfiguration($container, $server);
182 1
            $container->compile();
183 1
            $this->setContainer($container);
184 1
            $dumper = new PhpDumper($container);
185 1
            file_put_contents(self::SYMFONY_CACHE_PATH, $dumper->dump());
186
        } catch (ServiceNotFoundException | InvalidArgumentException $e) {
187
            throw new DoctrineStaticMetaException(
188
                'Exception building the container: ' . $e->getMessage(),
189
                $e->getCode(),
190
                $e
191
            );
192
        }
193 1
    }
194
195
    /**
196
     * Set a container instance
197
     *
198
     * @param ContainerInterface $container
199
     *
200
     * @return $this
201
     */
202 1
    public function setContainer(ContainerInterface $container): self
203
    {
204 1
        $this->container = $container;
205
206 1
        return $this;
207
    }
208
209
    /**
210
     * Build all the definitions, alias and other configuration for this container. Each of these steps need to be
211
     * carried out to allow the everything to work, however you may wish to change individual bits. Therefore this
212
     * method has been made final, but the individual methods can be overwritten if you extend off the class
213
     *
214
     * @param ContainerBuilder $container
215
     * @param array            $server
216
     *
217
     * @throws \Symfony\Component\DependencyInjection\Exception\InvalidArgumentException
218
     * @throws \Symfony\Component\DependencyInjection\Exception\ServiceNotFoundException
219
     */
220 1
    final public function addConfiguration(ContainerBuilder $container, array $server): void
221
    {
222 1
        $this->autoWireServices($container);
223 1
        $this->defineConfig($container, $server);
224 1
        $this->defineCache($container, $server);
225 1
        $this->defineEntityManager($container);
226 1
    }
227
228
    /**
229
     * This takes every class from the getServices method, auto wires them and marks them as public. You may wish to
230
     * override this if you want to mark certain classes as private
231
     *
232
     * @param ContainerBuilder $containerBuilder
233
     */
234 1
    public function autoWireServices(ContainerBuilder $containerBuilder): void
235
    {
236 1
        $services = $this->getServices();
237 1
        foreach ($services as $class) {
238 1
            $containerBuilder->autowire($class, $class)->setPublic(true);
239
        }
240 1
    }
241
242
    /**
243
     * This is a simple wrapper around the class constants. You can use this to add, remove, or replace individual
244
     * services that will be auto wired
245
     *
246
     * @return array
247
     */
248 1
    public function getServices(): array
249
    {
250 1
        return self::SERVICES;
251
    }
252
253
    /**
254
     * This is used to auto wire the config interface. It sets the $server param as a constructor argument and then
255
     * sets the concrete class as the implementation for the Interface. Override this if you wish to use different
256
     * logic for where the config comes from
257
     *
258
     * @param ContainerBuilder $containerBuilder
259
     * @param array            $server
260
     */
261 1
    public function defineConfig(ContainerBuilder $containerBuilder, array $server): void
262
    {
263 1
        $containerBuilder->getDefinition(Config::class)->setArgument('$server', $this->configVars($server));
264 1
        $containerBuilder->setAlias(ConfigInterface::class, Config::class);
265 1
    }
266
267
    /**
268
     * Take the $server array, normally a copy of $_SERVER, and pull out just the bits required by config
269
     *
270
     * @param array $server
271
     *
272
     * @return array
273
     */
274 1
    protected function configVars(array $server): array
275
    {
276 1
        $return = array_intersect_key(
277 1
            $server,
278 1
            array_flip(ConfigInterface::PARAMS)
279
        );
280
281 1
        return $return;
282
    }
283
284
    /**
285
     * This is used to auto wire the doctrine cache. If we are in dev mode then this will always use the Array Cache,
286
     * if not then the cache will be set to what is in the $server array. Override this method if you wish to use
287
     * different logic to handle caching
288
     *
289
     * @param ContainerBuilder $containerBuilder
290
     * @param array            $server
291
     */
292 1
    public function defineCache(ContainerBuilder $containerBuilder, array $server): void
293
    {
294 1
        $cacheDriver = $server[Config::PARAM_DOCTRINE_CACHE_DRIVER] ?? Config::DEFAULT_DOCTRINE_CACHE_DRIVER;
295 1
        $containerBuilder->autowire($cacheDriver);
296 1
        $this->configureFilesystemCache($containerBuilder);
297
        /**
298
         * Which Cache Driver is used for the Cache Interface?
299
         *
300
         * If Dev mode, we always use the Array Cache
301
         *
302
         * Otherwise, we use the Configured Cache driver (which defaults to Array Cache)
303
         */
304 1
        $cache = ($server[Config::PARAM_DEVMODE] ?? false) ? ArrayCache::class : $cacheDriver;
305 1
        $containerBuilder->setAlias(Cache::class, $cache);
306 1
        $containerBuilder->getDefinition(DoctrineCache::class)->addArgument(new Reference($cache));
307 1
    }
308
309 1
    private function configureFilesystemCache(ContainerBuilder $containerBuilder): void
310
    {
311 1
        $config = $this->getConfig($containerBuilder);
312 1
        $containerBuilder->getDefinition(FilesystemCache::class)
313 1
                         ->addArgument($config->get(Config::PARAM_FILESYSTEM_CACHE_PATH))
314 1
                         ->setPublic(true);
315 1
    }
316
317 1
    private function getConfig(ContainerBuilder $containerBuilder): Config
318
    {
319 1
        return $containerBuilder->get(Config::class);
320
    }
321
322
    /**
323
     * This is used to auto wire the entity manager. It first adds the DSM factory as the factory for the class, and
324
     * sets the Entity Manager as the implementation of the interface. Overrider this if you want to use your own
325
     * factory to create and configure the entity manager
326
     *
327
     * @param ContainerBuilder $container
328
     */
329 1
    public function defineEntityManager(ContainerBuilder $container): void
330
    {
331 1
        $container->getDefinition(EntityManagerInterface::class)
332 1
                  ->addArgument(new Reference(Config::class))
333 1
                  ->setFactory(
334
                      [
335 1
                          new Reference(EntityManagerFactory::class),
336 1
                          'getEntityManager',
337
                      ]
338
                  );
339 1
    }
340
341
    /**
342
     * @param string $id
343
     *
344
     * @return mixed
345
     * @SuppressWarnings(PHPMD.ShortVariable)
346
     * @throws DoctrineStaticMetaException
347
     */
348 1
    public function get($id)
349
    {
350
        try {
351 1
            return $this->container->get($id);
352
        } catch (ContainerExceptionInterface | NotFoundExceptionInterface $e) {
353
            throw new DoctrineStaticMetaException('Exception getting service ' . $id, $e->getCode(), $e);
0 ignored issues
show
Bug introduced by
The method getCode() does not exist on Psr\Container\ContainerExceptionInterface. It seems like you code against a sub-type of said class. However, the method does not exist in Psr\Container\NotFoundExceptionInterface or Symfony\Component\Depend...tion\ExceptionInterface. Are you sure you never get one of those? ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-call  annotation

353
            throw new DoctrineStaticMetaException('Exception getting service ' . $id, $e->/** @scrutinizer ignore-call */ getCode(), $e);
Loading history...
354
        }
355
    }
356
357
    /**
358
     * @param string $id
359
     * @SuppressWarnings(PHPMD.ShortVariable)
360
     *
361
     * @return bool|void
362
     */
363
    public function has($id)
364
    {
365
        return $this->container->has($id);
366
    }
367
}
368