Completed
Pull Request — master (#68)
by Christoffer
02:11
created

NoUnusedVariablesRule::enterNode()   A

Complexity

Conditions 3
Paths 4

Size

Total Lines 11
Code Lines 5

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
cc 3
eloc 5
nc 4
nop 1
dl 0
loc 11
rs 9.4285
c 0
b 0
f 0
1
<?php
2
3
namespace Digia\GraphQL\Validation\Rule;
4
5
use Digia\GraphQL\Error\ValidationException;
6
use Digia\GraphQL\Language\Node\NodeInterface;
7
use Digia\GraphQL\Language\Node\OperationDefinitionNode;
8
use Digia\GraphQL\Language\Node\VariableDefinitionNode;
9
use Digia\GraphQL\Language\Node\VariableNode;
10
use function Digia\GraphQL\Validation\unusedVariableMessage;
11
12
/**
13
 * No unused variables
14
 *
15
 * A GraphQL operation is only valid if all variables defined by an operation
16
 * are used, either directly or within a spread fragment.
17
 */
18
class NoUnusedVariablesRule extends AbstractRule
19
{
20
    /**
21
     * @var array|VariableDefinitionNode[]
22
     */
23
    protected $variableDefinitions;
24
25
    /**
26
     * @inheritdoc
27
     */
28
    public function enterNode(NodeInterface $node): ?NodeInterface
29
    {
30
        if ($node instanceof OperationDefinitionNode) {
31
            $this->variableDefinitions = [];
32
        }
33
34
        if ($node instanceof VariableDefinitionNode) {
35
            $this->variableDefinitions[] = $node;
36
        }
37
38
        return $node;
39
    }
40
41
    /**
42
     * @inheritdoc
43
     */
44
    public function leaveNode(NodeInterface $node): ?NodeInterface
45
    {
46
        if ($node instanceof OperationDefinitionNode) {
47
            $variableNamesUsed = [];
48
            $usages            = $this->validationContext->getRecursiveVariableUsages($node);
49
            $operationNameNode = $node->getName();
50
            $operationName     = null !== $operationNameNode ? $operationNameNode->getValue() : null;
51
52
            /** @var VariableNode $variableNode */
53
            foreach ($usages as ['node' => $variableNode]) {
54
                $variableNamesUsed[$variableNode->getNameValue()] = true;
55
            }
56
57
            foreach ($this->variableDefinitions as $variableDefinition) {
58
                $variableName = $variableDefinition->getVariable()->getNameValue();
59
60
                if (!isset($variableNamesUsed[$variableName])) {
61
                    $this->validationContext->reportError(
62
                        new ValidationException(
63
                            unusedVariableMessage($variableName, $operationName),
64
                            [$variableDefinition]
65
                        )
66
                    );
67
                }
68
            }
69
        }
70
71
        return $node;
72
    }
73
}
74