Completed
Push — master ( f94444...a44080 )
by Théo
02:35 queued 20s
created

FullyQualifiedNameResolver::resolveName()   A

Complexity

Conditions 2
Paths 2

Size

Total Lines 16
Code Lines 9

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 9
CRAP Score 2

Importance

Changes 0
Metric Value
cc 2
eloc 9
nc 2
nop 1
dl 0
loc 16
ccs 9
cts 9
cp 1
crap 2
rs 9.4285
c 0
b 0
f 0
1
<?php
2
3
declare(strict_types=1);
4
5
/*
6
 * This file is part of the humbug/php-scoper package.
7
 *
8
 * Copyright (c) 2017 Théo FIDRY <[email protected]>,
9
 *                    Pádraic Brady <[email protected]>
10
 *
11
 * For the full copyright and license information, please view the LICENSE
12
 * file that was distributed with this source code.
13
 */
14
15
namespace Humbug\PhpScoper\NodeVisitor\Resolver;
16
17
use Humbug\PhpScoper\NodeVisitor\AppendParentNode;
18
use Humbug\PhpScoper\NodeVisitor\Collection\NamespaceStmtCollection;
19
use Humbug\PhpScoper\NodeVisitor\Collection\UseStmtCollection;
20
use Humbug\PhpScoper\NodeVisitor\NameStmtPrefixer;
21
use PhpParser\Node\Expr\ConstFetch;
22
use PhpParser\Node\Expr\FuncCall;
23
use PhpParser\Node\Name;
24
use PhpParser\Node\Name\FullyQualified;
25
use function in_array;
26
27
/**
28
 * Attempts to resolve the node name into a fully qualified node. Returns a valid (non fully-qualified) name node on
29
 * failure.
30
 */
31
final class FullyQualifiedNameResolver
32
{
33
    private $namespaceStatements;
34
    private $useStatements;
35
36 346
    public function __construct(NamespaceStmtCollection $namespaceStatements, UseStmtCollection $useStatements)
37
    {
38 346
        $this->namespaceStatements = $namespaceStatements;
39 346
        $this->useStatements = $useStatements;
40
    }
41
42 262
    public function resolveName(Name $node): ResolvedValue
43
    {
44 262
        if ($node instanceof FullyQualified) {
45 136
            return new ResolvedValue($node, null, null);
46
        }
47
48 179
        $namespaceName = $this->namespaceStatements->findNamespaceForNode($node);
49
50 179
        $useName = $this->useStatements->findStatementForNode($namespaceName, $node);
51
52 179
        return new ResolvedValue(
53 179
            $this->resolveNodeName($node, $namespaceName, $useName),
54 179
            $namespaceName,
55 179
            $useName
56
        );
57
    }
58
59 179
    private function resolveNodeName(Name $name, ?Name $namespace, ?Name $use): Name
60
    {
61 179
        if (null !== $use) {
62 92
            return FullyQualified::concat($use, $name->slice(1), $name->getAttributes());
63
        }
64
65 117
        if (null === $namespace) {
66 60
            return new FullyQualified($name, $name->getAttributes());
67
        }
68
69 72
        if (in_array((string) $name, NameStmtPrefixer::PHP_FUNCTION_KEYWORDS, true)) {
70 1
            return $name;
71
        }
72
73 72
        $parentNode = AppendParentNode::getParent($name);
74
75
        if (
76 72
            ($parentNode instanceof ConstFetch || $parentNode instanceof FuncCall)
77 72
            && 1 === count($name->parts)
78
        ) {
79
            // Ambiguous name, cannot determine the FQ name
80 55
            return $name;
81
        }
82
83 26
        return FullyQualified::concat($namespace, $name, $name->getAttributes());
84
    }
85
}
86