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
Push — master ( c69350...98ccbf )
by Hong
02:45
created

Container::map()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 5
Code Lines 3

Duplication

Lines 0
Ratio 0 %

Importance

Changes 1
Bugs 0 Features 0
Metric Value
c 1
b 0
f 0
dl 0
loc 5
rs 9.4285
cc 1
eloc 3
nc 1
nop 2
1
<?php
2
/**
3
 * Phossa Project
4
 *
5
 * PHP version 5.4
6
 *
7
 * @category  Library
8
 * @package   Phossa2\Di
9
 * @copyright Copyright (c) 2016 phossa.com
10
 * @license   http://mit-license.org/ MIT License
11
 * @link      http://www.phossa.com/
12
 */
13
/*# declare(strict_types=1); */
14
15
namespace Phossa2\Di;
16
17
use Phossa2\Config\Config;
18
use Phossa2\Di\Message\Message;
19
use Phossa2\Di\Factory\Factory;
20
use Phossa2\Di\Resolver\Resolver;
21
use Phossa2\Di\Traits\ContainerTrait;
22
use Phossa2\Di\Traits\ArrayAccessTrait;
23
use Phossa2\Shared\Base\ObjectAbstract;
24
use Interop\Container\ContainerInterface;
25
use Phossa2\Di\Interfaces\ScopeInterface;
26
use Phossa2\Di\Exception\RuntimeException;
27
use Phossa2\Di\Exception\NotFoundException;
28
use Phossa2\Shared\Reference\DelegatorInterface;
29
use Phossa2\Config\Interfaces\WritableInterface;
30
use Phossa2\Di\Interfaces\FactoryAwareInterface;
31
use Phossa2\Di\Interfaces\ResolverAwareInterface;
32
use Phossa2\Shared\Reference\DelegatorAwareTrait;
33
use Phossa2\Di\Interfaces\ExtendedContainerInterface;
34
use Phossa2\Shared\Reference\DelegatorAwareInterface;
35
36
/**
37
 * Container
38
 *
39
 * A writable, array accessable, delegator-aware and extended instance container.
40
 *
41
 * - writable:
42
 *
43
 *   ```php
44
 *   $container->set('cache', $cache);
45
 *   ```
46
 *
47
 * - array accessable:
48
 *
49
 *   ```php
50
 *   // get
51
 *   $cache = $container['cache'];
52
 *
53
 *   // set/replace
54
 *   $container['cache'] = $anotherCache;
55
 *   ```
56
 *
57
 * - delegator-aware: lookup dependent instances in the delegator
58
 *
59
 *   ```php
60
 *   $delegator->addRegistry($container);
61
 *   ```
62
 *
63
 * - extended container
64
 *
65
 *   ```php
66
 *   // get new instance
67
 *   $newCache = $container->one('cache');
68
 *
69
 *   // run callables
70
 *   $container->run(['${#logger}', 'warning'], ['A warning message from ${user}']);
71
 *   ```
72
 *
73
 * @package Phossa2\Di
74
 * @author  Hong Zhang <[email protected]>
75
 * @see     ObjectAbstract
76
 * @see     ScopeInterface
77
 * @see     ContainerInterface
78
 * @see     ResolverAwareInterface
79
 * @see     FactoryAwareInterface
80
 * @see     ExtendedContainerInterface
81
 * @see     DelegatorAwareInterface
82
 * @see     WritableInterface
83
 * @see     \ArrayAccess
84
 * @version 2.0.0
85
 * @since   2.0.0 added
86
 */
87
class Container extends ObjectAbstract implements ContainerInterface, ResolverAwareInterface, FactoryAwareInterface, ScopeInterface, ExtendedContainerInterface, DelegatorAwareInterface, \ArrayAccess, WritableInterface
88
{
89
    use ContainerTrait, ArrayAccessTrait, DelegatorAwareTrait;
90
91
    /**
92
     * Inject a Phossa2\Config\Config
93
     *
94
     * ```php
95
     * $configData = [
96
     *     // container class
97
     *     'di.class' => 'Phossa2\\Di\\Container',
98
     *
99
     *     // container service definitions
100
     *     'di.service' => [
101
     *         // ...
102
     *     ],
103
     *
104
     *     // interface/classname mappings
105
     *     'di.mapping' => [
106
     *     ],
107
     *
108
     *     // init methods to run after container created
109
     *     'di.init' => [
110
     *         'default' => [],
111
     *         'mystuff' => [ ... ],
112
     *     ],
113
     * ];
114
     *
115
     * // instantiate $config
116
     * $config = new Config(null, null, $configData);
117
     *
118
     * // instantiate container
119
     * $container = new $config['di.class']($config);
120
     * ```
121
     *
122
     * @param  Config $config inject the config instance
123
     * @param  string $baseNode container's starting node in $config
124
     * @access public
125
     */
126
    public function __construct(
127
        Config $config = null,
128
        /*# string */ $baseNode = 'di'
129
    ) {
130
        $conf = $config ?: new Config();
131
132
        $this
133
            ->setResolver(new Resolver($this, $conf, $baseNode))
134
            ->setFactory(new Factory($this))
135
            ->registerObject('container', $this)
136
            ->registerObject('config', $conf)
137
            ->initContainer();
138
    }
139
140
    /**
141
     * Extensions to the Interop\Container\ContainerInterface
142
     *
143
     * - Accepting second param as object constructor arguments
144
     * - Accpeting $id with scope appended, e.g. 'cache@myScope'
145
     *
146
     * {@inheritDoc}
147
     */
148
    public function get($id)
149
    {
150
        // not found
151
        if (!$this->has($id)) {
152
            throw new NotFoundException(
153
                Message::get(Message::DI_SERVICE_NOTFOUND, $id),
154
                Message::DI_SERVICE_NOTFOUND
155
            );
156
        }
157
158
        // get the instance, constructor args if any
159
        return $this->getInstance(
160
            $id, func_num_args() > 1 ? func_get_arg(1) : []
161
        );
162
    }
163
164
    /**
165
     * Extensions to the Interop\Container\ContainerInterface
166
     *
167
     * - Accpeting $id with scope appended, e.g. 'cache@myScope'
168
     *
169
     * {@inheritDoc}
170
     */
171
    public function has($id)
172
    {
173
        if (is_string($id)) {
174
            return $this->getResolver()->hasService(
175
                $this->idWithoutScope($id)
176
            );
177
        }
178
        return false;
179
    }
180
181
    /**
182
     * {@inheritDoc}
183
     */
184
    public function set(/*# string */ $id, $value)
185
    {
186
        if ($this->isWritable()) {
187
            // set in service definition
188
            $this->getResolver()->setService(
189
                $this->idWithoutScope($id),
190
                $value
191
            );
192
            return $this;
193
        } else {
194
            throw new RuntimeException(
195
                Message::get(Message::DI_CONTAINER_READONLY, $id),
196
                Message::DI_CONTAINER_READONLY
197
            );
198
        }
199
    }
200
201
    /**
202
     * {@inheritDoc}
203
     */
204
    public function one(/*# string */ $id, array $arguments = [])
205
    {
206
        // set in single scope
207
        return $this->get(
208
            $this->scopedId($id, self::SCOPE_SINGLE),
209
            $arguments
210
        );
211
    }
212
213
    /**
214
     * {@inheritDoc}
215
     */
216
    public function run($callable, array $arguments = [])
217
    {
218
        // resolve any references in the callable(array) and arguments
219
        $this->resolve($callable);
220
        $this->resolve($arguments);
221
222
        return $this->getFactory()->executeCallable($callable, $arguments);
223
    }
224
225
    /**
226
     * {@inheritDoc}
227
     */
228
    public function map(/*# string */ $from, $to)
229
    {
230
        $this->getResolver()->setMapping($from, $to);
231
        return $this;
232
    }
233
234
    /**
235
     * {@inheritDoc}
236
     */
237
    public function resolve(&$toResolve)
238
    {
239
        $this->getResolver()->resolve($toResolve);
240
        return $this;
241
    }
242
243
    /**
244
     * Override `setDelegator()` from 'Phossa2\Shared\Reference\DelegatorAwareTrait'
245
     *
246
     * {@inheritDoc}
247
     */
248
    public function setDelegator(DelegatorInterface $delegator)
249
    {
250
        $this->delegator = $delegator;
251
252
        // this will make sure all dependencies will be looked up in the delegator
253
        $this->getResolver()->setObjectResolver();
254
255
        return $this;
256
    }
257
258
    /**
259
     * Override 'isWritable()' in 'Phossa2\Config\Traits\WritableTrait'
260
     *
261
     * Container's writability is depend on its resolver
262
     *
263
     * {@inheritDoc}
264
     */
265
    public function isWritable()/*# : bool */
266
    {
267
        return $this->getResolver()->isWritable();
268
    }
269
270
    /**
271
     * Register object in 'di.service' with $name
272
     *
273
     * e.g. `$this->registerObject('container', $this)`
274
     *
275
     * - Later, $this can be referenced as '${#container}' anywhere
276
     *
277
     * - $object will skip execute common methods for created instances.
278
     *
279
     *   instead of just do
280
     *      `$container->set($name, $object)`
281
     *
282
     *   you may do
283
     *      $container->set($name, ['class' => $object, 'skip' => true]);
284
     *
285
     * @param  string $name name to register with
286
     * @param  object $object
287
     * @return $this
288
     * @access protected
289
     */
290
    protected function registerObject(/*# string */ $name, $object)
291
    {
292
        if (!$this->has($name) && $this->isWritable()) {
293
            $this->set($name, ['class' => $object, 'skip' => true]);
294
        }
295
        return $this;
296
    }
297
}
298