Completed
Push — master ( 7643fe...abf786 )
by Jonathan-Paul
02:41
created

MongoDbServiceProvider   A

Complexity

Total Complexity 35

Size/Duplication

Total Lines 217
Duplicated Lines 0 %

Coupling/Cohesion

Components 1
Dependencies 2

Test Coverage

Coverage 100%

Importance

Changes 0
Metric Value
wmc 35
lcom 1
cbo 2
dl 0
loc 217
ccs 91
cts 91
cp 1
rs 9
c 0
b 0
f 0

12 Methods

Rating   Name   Duplication   Size   Complexity  
A __construct() 0 9 3
A buildConnectionString() 0 13 3
A buildUri() 0 4 1
A getArg() 0 4 2
A getArgConnectionAuthority() 0 9 2
A getArgConnectionHost() 0 12 4
A getArgConnectionHosts() 0 6 2
A getArgUri() 0 9 3
A getDefaultArg() 0 10 3
A loadParameters() 0 15 4
B loadSingletonParameters() 0 17 5
B register() 0 30 3
1
<?php
2
/**
3
 * MongoDB service provider for the Silex micro-framework.
4
 *
5
 * @see http://php.net/manual/set.mongodb.php
6
 */
7
8
namespace LiquidBox\Silex\Provider;
9
10
use MongoDB;
11
use Pimple\Container;
12
use Pimple\ServiceProviderInterface;
13
14
/**
15
 * MongoDb Provider.
16
 *
17
 * @author Jonathan-Paul Marois <[email protected]>
18
 */
19
class MongoDbServiceProvider implements ServiceProviderInterface
20
{
21
    /**
22
     * @var array Buffer.
23
     */
24
    private $args = array();
25
26
    /**
27
     * @var array
28
     */
29
    private $defaultArgs = array();
30
31
    /**
32
     * @var int|string
33
     */
34
    private $defaultConnection = 0;
35
36
    /**
37
     * @var string
38
     */
39
    private $id = 'mongodb';
40
41
    /**
42
     * @var string
43
     */
44
    private $instances = 'mongodb.clients';
45
46
    /**
47
     * @var bool
48
     */
49
    private $isLoaded = false;
50
51
    /**
52
     * @var array
53
     */
54
    private $parameters = array();
55
56
    /**
57
     * @param string $id
58
     * @param string $instances
59
     */
60 9
    public function __construct($id = null, $instances = null)
61
    {
62 9
        if (strlen($id)) {
63 1
            $this->id = $id;
64 1
        }
65 9
        if (strlen($instances)) {
66 1
            $this->instances = $instances;
67 1
        }
68 9
    }
69
70
    /**
71
     * @return string
72
     */
73 5
    private function buildConnectionString(array $connection)
74
    {
75 5
        $uri = $this->getArgConnectionAuthority($connection) . '/';
76
77 5
        if (!empty($connection['db'])) {
78 3
            $uri .= $connection['db'];
79 3
        }
80 5
        if (!empty($connection['options'])) {
81 1
            $uri .= '?' . http_build_query($connection['options']);
82 1
        }
83
84 5
        return rtrim($uri, '/');
85
    }
86
87
    /**
88
     * @param array|string $connection
89
     *
90
     * @return string
91
     */
92 5
    private function buildUri($connection)
93
    {
94 5
        return 'mongodb://' . $this->buildConnectionString($connection);
0 ignored issues
show
Bug introduced by
It seems like $connection defined by parameter $connection on line 92 can also be of type string; however, LiquidBox\Silex\Provider...buildConnectionString() does only seem to accept array, maybe add an additional type check?

This check looks at variables that have been passed in as parameters and are passed out again to other methods.

If the outgoing method call has stricter type requirements than the method itself, an issue is raised.

An additional type check may prevent trouble.

Loading history...
95
    }
96
97
    /**
98
     * @param \Pimple\Container $app
99
     * @param string            $name
100
     *
101
     * @return string
102
     */
103 9
    private function getArg(Container $app, $name)
104
    {
105 9
        return isset($this->args[$name]) ? $this->args[$name] : $this->getDefaultArg($app, $name);
106
    }
107
108 5
    private function getArgConnectionAuthority(array $connection)
109
    {
110 5
        if (empty($connection['user'])) {
111 2
            return $this->getArgConnectionHost($connection);
112
        }
113
114 3
        return $connection['user'] . ':' . rawurlencode($connection['pwd']) . '@' .
115 3
            $this->getArgConnectionHost($connection);
116
    }
117
118
    /**
119
     * @return string
120
     */
121 5
    private function getArgConnectionHost(array $connection = array())
122
    {
123 5
        if (!empty($connection['hosts'])) {
124 1
            return $this->getArgConnectionHosts($connection);
125
        }
126
127 5
        if (empty($connection['host'])) {
128 4
            $connection['host'] = '127.0.0.1';
129 4
        }
130
131 5
        return empty($connection['port']) ? $connection['host'] : $connection['host'] . ':' . $connection['port'];
132
    }
133
134 1
    private function getArgConnectionHosts(array $connection)
135
    {
136
        return implode(',', array_map(function ($hosts) {
137 1
            return $this->getArgConnectionHost(is_array($hosts) ? $hosts : array('host' => $hosts));
138 1
        }, $connection['hosts']));
139
    }
140
141
    /**
142
     * @return string
143
     */
144 9
    private function getArgUri()
145
    {
146 9
        if (!empty($this->args['uri'])) {
147 2
            return $this->args['uri'];
148
        }
149 7
        if (!empty($this->args['connection'])) {
150 5
            return $this->args['connection'];
151
        }
152 2
    }
153
154
    /**
155
     * @param \Pimple\Container $app
156
     * @param string            $name
157
     *
158
     * @return string|array
159
     */
160 8
    private function getDefaultArg(Container $app, $name)
161
    {
162 8
        if (!isset($this->defaultArgs[$name])) {
163 8
            $this->defaultArgs[$name] = empty($app['mongodb.' . $name]) ?
164 8
                array('uri_options' => array(), 'driver_options' => array())[$name] :
165 1
                $app['mongodb.' . $name];
166 8
        }
167
168 8
        return $this->defaultArgs[$name];
169
    }
170
171 9
    private function loadParameters(Container $app)
172
    {
173 9
        if ($this->isLoaded) {
174 9
            return;
175
        }
176
177 9
        $this->isLoaded = true;
178
179 9
        if (empty($app['mongodb.uri']) || !is_array($app['mongodb.uri'])) {
180 8
            $this->loadSingletonParameters($app);
181 8
        } else {
182 1
            $this->parameters = $app['mongodb.uri'];
183 1
            $this->defaultConnection = array_keys($this->parameters)[0];
184
        }
185 9
    }
186
187 8
    private function loadSingletonParameters(Container $app)
188
    {
189 8
        $this->parameters[0] = array();
190
191 8
        if (!empty($app['mongodb.uri'])) {
192 2
            $this->parameters[0]['uri'] = $app['mongodb.uri'];
193 8
        } elseif (!empty($app['mongodb.connection'])) {
194 4
            $this->parameters[0]['connection'] = $app['mongodb.connection'];
195 4
        }
196
197 8
        if (!empty($app['mongodb.uri_options'])) {
198 1
            $this->parameters[0]['uri_options'] = $app['mongodb.uri_options'];
199 1
        }
200 8
        if (!empty($app['mongodb.driver_options'])) {
201 1
            $this->parameters[0]['driver_options'] = $app['mongodb.driver_options'];
202 1
        }
203 8
    }
204
205 9
    public function register(Container $app)
206
    {
207
        $app[$this->id] = function () use ($app) {
208 9
            $this->loadParameters($app);
209
210 9
            return $app[$this->instances][$this->defaultConnection];
211
        };
212
        $app[$this->instances] = function () use ($app) {
213 9
            $this->loadParameters($app);
214
215 9
            $instances = new Container();
216 9
            foreach ($this->parameters as $client => $this->args) {
217
                $instances[$client] = function () use ($app) {
218 9
                    return $app['mongodb.client'](
219 9
                        $this->getArgUri(),
220 9
                        $this->getArg($app, 'uri_options'),
221 9
                        $this->getArg($app, 'driver_options')
222 9
                    );
223
                };
224 9
            }
225
226 9
            return $instances;
227
        };
228
229 9
        $app['mongodb.client'] = $app->protect(
230 9
            function ($uri = null, array $uriOptions = array(), array $driverOptions = array()) {
231 9
                return new MongoDB\Client(is_array($uri) ? $this->buildUri($uri) : $uri, $uriOptions, $driverOptions);
232
            }
233 9
        );
234 9
    }
235
}
236