Passed
Push — master ( d3a94c...76e109 )
by Valentin
05:50
created

AddUseStmts   A

Complexity

Total Complexity 18

Size/Duplication

Total Lines 105
Duplicated Lines 0 %

Coupling/Cohesion

Components 1
Dependencies 7

Importance

Changes 0
Metric Value
wmc 18
lcom 1
cbo 7
dl 0
loc 105
rs 10
c 0
b 0
f 0

7 Methods

Rating   Name   Duplication   Size   Complexity  
A __construct() 0 4 1
A leaveNode() 0 9 2
A definePlacementID() 0 10 3
A removeDuplicates() 0 18 5
A getExistingUseParts() 0 15 4
A buildUseStmts() 0 9 2
A buildUseStmt() 0 6 1
1
<?php
2
declare(strict_types=1);
3
4
namespace Cycle\ORM\Promise\Visitor;
5
6
use Cycle\ORM\Promise\Utils;
7
use PhpParser\Builder\Use_;
8
use PhpParser\Node;
9
use PhpParser\NodeVisitorAbstract;
10
11
/**
12
 * Add use statement to the code.
13
 */
14
class AddUseStmts extends NodeVisitorAbstract
15
{
16
    /** @var array */
17
    private $useStmts = [];
18
19
    public function __construct(array $useStmts)
20
    {
21
        $this->useStmts = $useStmts;
22
    }
23
24
    /**
25
     * {@inheritdoc}
26
     */
27
    public function leaveNode(Node $node)
28
    {
29
        if ($node instanceof Node\Stmt\Namespace_) {
30
            $placementID = $this->definePlacementID($node);
31
            $node->stmts = Utils::injectValues($node->stmts, $placementID, $this->removeDuplicates($node->stmts, $this->buildUseStmts()));
0 ignored issues
show
Documentation introduced by
$this->buildUseStmts() is of type array<integer,object<PhpParser\Node>>, but the function expects a array<integer,object<PhpParser\Node\Stmt\Use_>>.

It seems like the type of the argument is not accepted by the function/method which you are calling.

In some cases, in particular if PHP’s automatic type-juggling kicks in this might be fine. In other cases, however this might be a bug.

We suggest to add an explicit type cast like in the following example:

function acceptsInteger($int) { }

$x = '123'; // string "123"

// Instead of
acceptsInteger($x);

// we recommend to use
acceptsInteger((integer) $x);
Loading history...
32
        }
33
34
        return null;
35
    }
36
37
    private function definePlacementID(Node\Stmt\Namespace_ $node): int
38
    {
39
        foreach ($node->stmts as $index => $child) {
40
            if ($child instanceof Node\Stmt\Class_) {
41
                return $index;
42
            }
43
        }
44
45
        return 0;
46
    }
47
48
    /**
49
     * @param Node\Stmt[]      $stmts
50
     * @param Node\Stmt\Use_[] $nodes
51
     *
52
     * @return Node\Stmt\Use_[]
53
     */
54
    private function removeDuplicates(array $stmts, array $nodes): array
55
    {
56
        $uses = $this->getExistingUseParts($stmts);
57
58
        foreach ($nodes as $i => $node) {
59
            if (!$node instanceof Node\Stmt\Use_) {
60
                continue;
61
            }
62
63
            foreach ($node->uses as $use) {
64
                if (in_array($use->name->parts, $uses)) {
65
                    unset($nodes[$i]);
66
                }
67
            }
68
        }
69
70
        return $nodes;
71
    }
72
73
    /**
74
     * @param Node\Stmt[] $stmts
75
     *
76
     * @return string[]
77
     */
78
    private function getExistingUseParts(array $stmts): array
79
    {
80
        $parts = [];
81
        foreach ($stmts as $stmt) {
82
            if (!$stmt instanceof Node\Stmt\Use_) {
83
                continue;
84
            }
85
86
            foreach ($stmt->uses as $use) {
87
                $parts[] = $use->name->parts;
88
            }
89
        }
90
91
        return $parts;
92
    }
93
94
    /**
95
     * @return Node[]
96
     */
97
    private function buildUseStmts(): array
98
    {
99
        $stmts = [];
100
        foreach ($this->useStmts as $useStmt) {
101
            $stmts[] = $this->buildUseStmt($useStmt);
102
        }
103
104
        return $stmts;
105
    }
106
107
    /**
108
     * @param string $type
109
     *
110
     * @return Node
111
     */
112
    private function buildUseStmt(string $type): Node
113
    {
114
        $use_ = new Use_(new Node\Name($type), Node\Stmt\Use_::TYPE_NORMAL);
115
116
        return $use_->getNode();
117
    }
118
}