Test Failed
Pull Request — master (#37)
by Divine Niiquaye
15:08
created

ValueDefinition   A

Complexity

Total Complexity 17

Size/Duplication

Total Lines 86
Duplicated Lines 0 %

Importance

Changes 3
Bugs 0 Features 0
Metric Value
wmc 17
eloc 33
c 3
b 0
f 0
dl 0
loc 86
rs 10

4 Methods

Rating   Name   Duplication   Size   Complexity  
A __construct() 0 4 1
A replace() 0 11 4
B build() 0 36 11
A getEntity() 0 3 1
1
<?php
2
3
declare(strict_types=1);
4
5
/*
6
 * This file is part of DivineNii opensource projects.
7
 *
8
 * PHP version 7.4 and above required
9
 *
10
 * @author    Divine Niiquaye Ibok <[email protected]>
11
 * @copyright 2021 DivineNii (https://divinenii.com/)
12
 * @license   https://opensource.org/licenses/BSD-3-Clause License
13
 *
14
 * For the full copyright and license information, please view the LICENSE
15
 * file that was distributed with this source code.
16
 */
17
18
namespace Rade\DI\Definitions;
19
20
use PhpParser\Node\Expr;
21
use PhpParser\Node\Stmt\Return_;
22
use Rade\DI\Exceptions\ServiceCreationException;
23
use Rade\DI\Resolver;
24
25
/**
26
 * Represents a definition service that shouldn't be resolved.
27
 *
28
 * @author Divine Niiquaye Ibok <[email protected]>
29
 */
30
class ValueDefinition implements DefinitionInterface, ShareableDefinitionInterface, DepreciableDefinitionInterface
31
{
32
    use Traits\DeprecationTrait;
33
    use Traits\VisibilityTrait;
34
35
    /** @var mixed */
36
    private $value;
37
38
    /**
39
     * Definition constructor.
40
     *
41
     * @param mixed $value
42
     */
43
    public function __construct($value, bool $shared = true)
44
    {
45
        $this->replace($value);
46
        $this->shared = $shared;
47
    }
48
49
    /**
50
     * Replace the existing value.
51
     *
52
     * @param mixed $value
53
     *
54
     * @return $this
55
     */
56
    public function replace($value)
57
    {
58
        if ($value instanceof DefinitionInterface) {
59
            throw new ServiceCreationException(\sprintf('A definition entity must not be an instance of "%s".', DefinitionInterface::class));
60
        } elseif ($value instanceof \PhpParser\Node && !$value instanceof Expr) {
61
            throw new ServiceCreationException(\sprintf('A definition entity must be an instance of "%s".', Expr::class));
62
        }
63
64
        $this->value = $value;
65
66
        return $this;
67
    }
68
69
    /**
70
     * {@inheritdoc}
71
     */
72
    public function getEntity()
73
    {
74
        return $this->value;
75
    }
76
77
    /**
78
     * {@inheritdoc}
79
     */
80
    public function build(string $id, Resolver $resolver)
81
    {
82
        if (null === $builder = $resolver->getBuilder()) {
83
            if ($this->isDeprecated()) {
84
                $this->triggerDeprecation($id);
85
            }
86
87
            return \is_array($value = $this->value) ? $resolver->resolveArguments($value) : $value;
88
        }
89
90
        $defNode = $builder->method($resolver->createMethod($id))->makeProtected();
91
92
        if ($this->value instanceof \PhpParser\Node) {
93
            if ($this->value instanceof Expr\Array_) {
94
                $defNode->setReturnType('array');
95
            } elseif ($this->value instanceof Expr\New_) {
96
                $defNode->setReturnType($this->value->class->toString());
0 ignored issues
show
Bug introduced by
The method toString() does not exist on PhpParser\Node\Expr. ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-call  annotation

96
                $defNode->setReturnType($this->value->class->/** @scrutinizer ignore-call */ toString());

This check looks for calls to methods that do not seem to exist on a given type. It looks for the method on the type itself as well as in inherited classes or implemented interfaces.

This is most likely a typographical error or the method has been renamed.

Loading history...
Bug introduced by
The method toString() does not exist on PhpParser\Node\Stmt\Class_. ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-call  annotation

96
                $defNode->setReturnType($this->value->class->/** @scrutinizer ignore-call */ toString());

This check looks for calls to methods that do not seem to exist on a given type. It looks for the method on the type itself as well as in inherited classes or implemented interfaces.

This is most likely a typographical error or the method has been renamed.

Loading history...
97
            }
98
        } else {
99
            $defNode->setReturnType(\get_debug_type($this->value));
100
        }
101
102
        if ($this->isDeprecated()) {
103
            $defNode->addStmt($this->triggerDeprecation($id, $builder));
104
        }
105
106
        if ($this->lazy) {
107
            $lazyMethod = \is_array($this->value) ? 'resolveArguments' : 'resolve';
108
            $createdValue = $builder->methodCall($builder->propertyFetch($builder->var('this'), 'resolver'), $lazyMethod, [$this->value]);
109
        }
110
111
        if ($this->shared) {
112
            $createdValue = $this->triggerSharedBuild($id, $createdValue ?? $builder->val($this->value), $builder);
113
        }
114
115
        return $defNode->addStmt(new Return_($createdValue ?? $builder->val($this->value)));
116
    }
117
}
118