Completed
Push — master ( c5de01...c9c19d )
by
unknown
07:34 queued 05:10
created

ServiceContainer   A

Complexity

Total Complexity 15

Size/Duplication

Total Lines 130
Duplicated Lines 0 %

Coupling/Cohesion

Components 2
Dependencies 0

Importance

Changes 0
Metric Value
wmc 15
lcom 2
cbo 0
dl 0
loc 130
rs 10
c 0
b 0
f 0

9 Methods

Rating   Name   Duplication   Size   Complexity  
A hasParameter() 0 4 1
A setParameter() 0 4 1
A getParameter() 0 8 2
A hasService() 0 4 1
A removeService() 0 6 2
A setDefinition() 0 5 1
A setStaticDefinition() 0 11 2
A getService() 0 8 2
A getServicesByTag() 0 11 3
1
<?php
2
3
namespace Coduo\TuTu;
4
5
/**
6
 * Simple service container inspired by PhpSpec/ServiceContainer class which was created on top of Pimple.
7
 */
8
class ServiceContainer
9
{
10
    /**
11
     * @var array
12
     */
13
    private $parameters = [];
14
15
    /**
16
     * @var array
17
     */
18
    private $serviceDefinitions = [];
19
20
    /**
21
     * @var array
22
     */
23
    private $tags = [];
24
25
    /**
26
     * @param $id
27
     * @return bool
28
     */
29
    public function hasParameter($id)
30
    {
31
        return array_key_exists($id, $this->parameters);
32
    }
33
34
    /**
35
     * @param $id
36
     * @param $value
37
     */
38
    public function setParameter($id, $value)
39
    {
40
        $this->parameters[$id] = $value;
41
    }
42
43
    /**
44
     * @param $id
45
     * @return mixed
46
     * @throws \RuntimeException
47
     */
48
    public function getParameter($id)
49
    {
50
        if (!array_key_exists($id, $this->parameters)) {
51
            throw new \RuntimeException(sprintf("Service container does not have parameter with id \"%s\"", $id));
52
        }
53
54
        return $this->parameters[$id];
55
    }
56
57
    /**
58
     * @param $id
59
     * @return bool
60
     */
61
    public function hasService($id)
62
    {
63
        return array_key_exists($id, $this->serviceDefinitions);
64
    }
65
66
67
    public function removeService($id)
68
    {
69
        if ($this->hasService($id)){
70
            unset($this->serviceDefinitions[$id]);
71
        }
72
    }
73
74
    /**
75
     * getService($id) will return result of $definition closure.
76
     * Callback will be executed with $this (ServiceContainer) as a argument.
77
     *
78
     * @param $id
79
     * @param callable $definition
80
     * @param array $tags
81
     */
82
    public function setDefinition($id, \Closure $definition, $tags = [])
83
    {
84
        $this->serviceDefinitions[$id] = $definition;
85
        $this->tags[$id] = $tags;
86
    }
87
88
    /**
89
     * Works just like setDefinition but getService($id) is going to return
90
     * exactly same value every single time.
91
     *
92
     * @param $id
93
     * @param callable $definition
94
     * @param array $tags
95
     */
96
    public function setStaticDefinition($id, \Closure $definition, $tags = [])
97
    {
98
        $this->setDefinition($id, function ($container) use ($definition) {
99
            static $instance;
100
            if (!isset($instance)) {
101
                $instance = $definition($container);
102
            }
103
104
            return $instance;
105
        }, $tags);
106
    }
107
108
    /**
109
     * @param $id
110
     * @return mixed
111
     * @throws \RuntimeException
112
     */
113
    public function getService($id)
114
    {
115
        if (!array_key_exists($id, $this->serviceDefinitions)) {
116
            throw new \RuntimeException("Service container does not have service with id \"key\"");
117
        }
118
119
        return $this->serviceDefinitions[$id]($this);
120
    }
121
122
    /**
123
     * @param $tag
124
     * @return array
125
     */
126
    public function getServicesByTag($tag)
127
    {
128
        $services = [];
129
        foreach ($this->tags as $serviceId => $tags) {
130
            if (in_array($tag, $tags, true)) {
131
                $services[] = $this->getService($serviceId);
132
            }
133
        }
134
135
        return $services;
136
    }
137
}
138