RepositoryContainer::makeRepositoryList()   A
last analyzed

Complexity

Conditions 5
Paths 9

Size

Total Lines 13
Code Lines 9

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 10
CRAP Score 5

Importance

Changes 1
Bugs 0 Features 0
Metric Value
cc 5
eloc 9
nc 9
nop 0
dl 0
loc 13
ccs 10
cts 10
cp 1
crap 5
rs 9.6111
c 1
b 0
f 0
1
<?php
2
3
declare(strict_types=1);
4
5
namespace Yiisoft\Yii\Cycle\Factory;
6
7
use Cycle\ORM\ORMInterface;
8
use Cycle\ORM\RepositoryInterface;
9
use Cycle\ORM\SchemaInterface;
10
use Psr\Container\ContainerInterface;
11
use Yiisoft\Yii\Cycle\Exception\NotFoundException;
12
use Yiisoft\Yii\Cycle\Exception\NotInstantiableClassException;
13
14
use function is_string;
15
16
final class RepositoryContainer implements ContainerInterface
17
{
18
    private ORMInterface $orm;
19
20
    private bool $rolesBuilt = false;
21
    private array $roles = [];
22
23
    private array $instances = [];
24
25 6
    public function __construct(ContainerInterface $rootContainer)
26
    {
27 6
        $this->orm = $rootContainer->get(ORMInterface::class);
28
    }
29
30 4
    public function get($id)
31
    {
32 4
        if (isset($this->instances[$id])) {
33 1
            return $this->instances[$id];
34
        }
35
36 4
        if ($this->has($id)) {
37 2
            return $this->instances[$id] = $this->makeRepository($this->roles[$id]);
38
        }
39
40 2
        if (!is_subclass_of($id, RepositoryInterface::class)) {
41 1
            throw new NotInstantiableClassException($id);
42
        }
43
44 1
        throw new NotFoundException($id);
45
    }
46
47 6
    public function has($id): bool
48
    {
49 6
        if (!is_subclass_of($id, RepositoryInterface::class)) {
50 2
            return false;
51
        }
52
53 4
        if (!$this->rolesBuilt) {
54 4
            $this->makeRepositoryList();
55 4
            $this->rolesBuilt = true;
56
        }
57
58 4
        return isset($this->roles[$id]);
59
    }
60
61 4
    private function makeRepositoryList(): void
62
    {
63 4
        $schema = $this->orm->getSchema();
64 4
        $roles = [];
65 4
        foreach ($schema->getRoles() as $role) {
66 3
            $repository = $schema->define($role, SchemaInterface::REPOSITORY);
67 3
            if (is_string($repository)) {
68 3
                $roles[$repository][] = $role;
69
            }
70
        }
71 4
        foreach ($roles as $repository => $role) {
72 3
            if (count($role) === 1) {
73 3
                $this->roles[$repository] = current($role);
74
            }
75
        }
76
    }
77
78
    /**
79
     * @psalm-param class-string $role
80
     */
81 2
    private function makeRepository(string $role): RepositoryInterface
82
    {
83 2
        return $this->orm->getRepository($role);
84
    }
85
}
86