diff --git a/src/Rules/Node/ValidConstantFunctionRule.php b/src/Rules/Node/ValidConstantFunctionRule.php index 0a55b81f..16a127f0 100644 --- a/src/Rules/Node/ValidConstantFunctionRule.php +++ b/src/Rules/Node/ValidConstantFunctionRule.php @@ -26,17 +26,28 @@ public function enterNode(Node $node, Environment $env): Node } $arguments = $node->getNode('arguments'); - if (1 !== $arguments->count()) { - return $node; + $argument = $arguments->hasNode('0') ? $arguments->getNode('0') : null; + // Try for named parameters + if (null === $argument && $arguments->hasNode('constant')) { + $argument = $arguments->getNode('constant'); } - - $argument = $arguments->getNode('0'); if (!$argument instanceof ConstantExpression) { return $node; } $constant = $argument->getAttribute('value'); if (!\is_string($constant)) { + $this->addError( + 'The first param of the function "constant()" must be a string.', + $node, + 'StringConstant' + ); + + return $node; + } + + // The object to get the constant from cannot be resolved statically. + if (1 !== $arguments->count()) { return $node; } @@ -46,7 +57,7 @@ public function enterNode(Node $node, Environment $env): Node if ('::class' === strtolower(substr($constant, -7))) { $this->addError( - sprintf('You cannot use the Twig function "constant()" to access "%s". You could provide an object and call constant("class", $object) or use the class name directly as a string.', $constant), + 'You cannot use the function "constant()" to access class names.', $node, 'ClassConstant' ); diff --git a/tests/Rules/Node/ValidConstantFunction/ValidConstantFunctionRuleTest.php b/tests/Rules/Node/ValidConstantFunction/ValidConstantFunctionRuleTest.php index 322c854c..29979765 100644 --- a/tests/Rules/Node/ValidConstantFunction/ValidConstantFunctionRuleTest.php +++ b/tests/Rules/Node/ValidConstantFunction/ValidConstantFunctionRuleTest.php @@ -15,7 +15,11 @@ public function testRule(): void { $this->checkRule(new ValidConstantFunctionRule(), [ 'ValidConstantFunction.ConstantUndefined:7' => 'Constant "ThisDoesNotExist::SomeKey" is undefined.', - 'ValidConstantFunction.ClassConstant:9' => 'You cannot use the Twig function "constant()" to access "ThisDoesNotExist::class". You could provide an object and call constant("class", $object) or use the class name directly as a string.', + 'ValidConstantFunction.ClassConstant:9' => 'You cannot use the function "constant()" to access class names.', + 'ValidConstantFunction.StringConstant:10' => 'The first param of the function "constant()" must be a string.', + 'ValidConstantFunction.ConstantUndefined:17' => 'Constant "ThisDoesNotExist::SomeKey" is undefined.', + 'ValidConstantFunction.ClassConstant:19' => 'You cannot use the function "constant()" to access class names.', + 'ValidConstantFunction.StringConstant:20' => 'The first param of the function "constant()" must be a string.', ]); } } diff --git a/tests/Rules/Node/ValidConstantFunction/ValidConstantFunctionRuleTest.twig b/tests/Rules/Node/ValidConstantFunction/ValidConstantFunctionRuleTest.twig index d8f394c9..ba73b80f 100644 --- a/tests/Rules/Node/ValidConstantFunction/ValidConstantFunctionRuleTest.twig +++ b/tests/Rules/Node/ValidConstantFunction/ValidConstantFunctionRuleTest.twig @@ -8,5 +8,16 @@ {{ constant(someVar) }} {{ constant('ThisDoesNotExist::class') }} {{ constant(1) }} + + {{ constant(constant='DateTimeInterface::ATOM') }} + {{ constant(constant='DATE_ATOM') }} + {{ constant(constant='TwigCsFixer\\Tests\\Rules\\Node\\ValidConstantFunction\\ValidConstantFunctionRuleTest::SOME_CONSTANT') }} + {{ constant(constant='class', someObject) }} + + {{ constant(constant='ThisDoesNotExist::SomeKey') }} + {{ constant(constant=someVar) }} + {{ constant(constant='ThisDoesNotExist::class') }} + {{ constant(constant=1) }} + {{ notConstant('ThisDoesNotExist::class') }} {% endblock %}