Completed
Pull Request — master (#3354)
by Michael
61:13
created

TypeRegistry::override()   A

Complexity

Conditions 3
Paths 3

Size

Total Lines 11
Code Lines 5

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
eloc 5
dl 0
loc 11
rs 10
c 0
b 0
f 0
cc 3
nc 3
nop 2
1
<?php
2
3
declare(strict_types=1);
4
5
namespace Doctrine\DBAL\Types;
6
7
use Doctrine\DBAL\DBALException;
8
use function array_search;
9
use function in_array;
10
11
/**
12
 * The type registry is responsible for holding a map of all known DBAL types.
13
 * The types are stored using the flyweight pattern so that one type only exists as exactly one instance.
14
 *
15
 * @internal TypeRegistry exists for forward compatibility, its API should not be considered stable.
16
 */
17
final class TypeRegistry
18
{
19
    /** @var array<string, Type> Map of type names and their corresponding flyweight objects. */
20
    private $instances = [];
21
22
    /**
23
     * Finds a type by the given name.
24
     *
25
     * @throws DBALException
26
     */
27
    public function get(string $name) : Type
28
    {
29
        if (! isset($this->instances[$name])) {
30
            throw DBALException::unknownColumnType($name);
31
        }
32
33
        return $this->instances[$name];
34
    }
35
36
    /**
37
     * Finds a name for the given type.
38
     *
39
     * @throws DBALException
40
     */
41
    public function lookupName(Type $type) : string
42
    {
43
        $name = $this->findTypeName($type);
44
45
        if ($name === null) {
46
            throw DBALException::typeNotRegistered($type);
47
        }
48
49
        return $name;
50
    }
51
52
    /**
53
     * Checks if there is a type of the given name.
54
     */
55
    public function has(string $name) : bool
56
    {
57
        return isset($this->instances[$name]);
58
    }
59
60
    /**
61
     * Registers a custom type to the type map.
62
     *
63
     * @throws DBALException
64
     */
65
    public function register(string $name, Type $type) : void
66
    {
67
        if (isset($this->instances[$name])) {
68
            throw DBALException::typeExists($name);
69
        }
70
71
        if ($this->findTypeName($type) !== null) {
72
            throw DBALException::typeAlreadyRegistered($type);
73
        }
74
75
        $this->instances[$name] = $type;
76
    }
77
78
    /**
79
     * Overrides an already defined type to use a different implementation.
80
     *
81
     * @throws DBALException
82
     */
83
    public function override(string $name, Type $type) : void
84
    {
85
        if (! isset($this->instances[$name])) {
86
            throw DBALException::typeNotFound($name);
87
        }
88
89
        if (! in_array($this->findTypeName($type), [$name, null], true)) {
90
            throw DBALException::typeAlreadyRegistered($type);
91
        }
92
93
        $this->instances[$name] = $type;
94
    }
95
96
    /**
97
     * Gets the map of all registered types and their corresponding type instances.
98
     *
99
     * @internal
100
     *
101
     * @return array<string, Type>
102
     */
103
    public function getMap() : array
104
    {
105
        return $this->instances;
106
    }
107
108
    private function findTypeName(Type $type) : ?string
109
    {
110
        $name = array_search($type, $this->instances, true);
111
112
        if ($name === false) {
113
            return null;
114
        }
115
116
        return $name;
117
    }
118
}
119